mirror of
https://github.com/lidarr/lidarr.git
synced 2025-07-16 10:03:51 -07:00
Changed: Remove Language Profiles (#870)
* Changed: Remove Language Profiles * fixup! Changed: Remove Language Profiles * fixup! Changed: Remove Language Profiles * Remove unused method in FileNameBuilder * Fixed: Cleanup Int Converter Copy/Paste Issues and Grammar
This commit is contained in:
parent
8f791abbf6
commit
8b860bcb82
227 changed files with 345 additions and 5873 deletions
|
@ -1,4 +1,3 @@
|
||||||
.language,
|
|
||||||
.quality {
|
.quality {
|
||||||
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,6 @@ import IconButton from 'Components/Link/IconButton';
|
||||||
import RelativeDateCellConnector from 'Components/Table/Cells/RelativeDateCellConnector';
|
import RelativeDateCellConnector from 'Components/Table/Cells/RelativeDateCellConnector';
|
||||||
import TableRow from 'Components/Table/TableRow';
|
import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import ArtistNameLink from 'Artist/ArtistNameLink';
|
import ArtistNameLink from 'Artist/ArtistNameLink';
|
||||||
import BlacklistDetailsModal from './BlacklistDetailsModal';
|
import BlacklistDetailsModal from './BlacklistDetailsModal';
|
||||||
|
@ -42,7 +41,6 @@ class BlacklistRow extends Component {
|
||||||
const {
|
const {
|
||||||
artist,
|
artist,
|
||||||
sourceTitle,
|
sourceTitle,
|
||||||
language,
|
|
||||||
quality,
|
quality,
|
||||||
date,
|
date,
|
||||||
protocol,
|
protocol,
|
||||||
|
@ -84,19 +82,6 @@ class BlacklistRow extends Component {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name === 'language') {
|
|
||||||
return (
|
|
||||||
<TableRowCell
|
|
||||||
key={name}
|
|
||||||
className={styles.language}
|
|
||||||
>
|
|
||||||
<TrackLanguage
|
|
||||||
language={language}
|
|
||||||
/>
|
|
||||||
</TableRowCell>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name === 'quality') {
|
if (name === 'quality') {
|
||||||
return (
|
return (
|
||||||
<TableRowCell
|
<TableRowCell
|
||||||
|
@ -172,7 +157,6 @@ BlacklistRow.propTypes = {
|
||||||
id: PropTypes.number.isRequired,
|
id: PropTypes.number.isRequired,
|
||||||
artist: PropTypes.object.isRequired,
|
artist: PropTypes.object.isRequired,
|
||||||
sourceTitle: PropTypes.string.isRequired,
|
sourceTitle: PropTypes.string.isRequired,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
date: PropTypes.string.isRequired,
|
date: PropTypes.string.isRequired,
|
||||||
protocol: PropTypes.string.isRequired,
|
protocol: PropTypes.string.isRequired,
|
||||||
|
|
|
@ -6,7 +6,6 @@ import RelativeDateCellConnector from 'Components/Table/Cells/RelativeDateCellCo
|
||||||
import TableRow from 'Components/Table/TableRow';
|
import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import AlbumTitleLink from 'Album/AlbumTitleLink';
|
import AlbumTitleLink from 'Album/AlbumTitleLink';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import ArtistNameLink from 'Artist/ArtistNameLink';
|
import ArtistNameLink from 'Artist/ArtistNameLink';
|
||||||
import HistoryEventTypeCell from './HistoryEventTypeCell';
|
import HistoryEventTypeCell from './HistoryEventTypeCell';
|
||||||
|
@ -55,8 +54,6 @@ class HistoryRow extends Component {
|
||||||
artist,
|
artist,
|
||||||
album,
|
album,
|
||||||
track,
|
track,
|
||||||
language,
|
|
||||||
languageCutoffNotMet,
|
|
||||||
quality,
|
quality,
|
||||||
qualityCutoffNotMet,
|
qualityCutoffNotMet,
|
||||||
eventType,
|
eventType,
|
||||||
|
@ -128,17 +125,6 @@ class HistoryRow extends Component {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name === 'language') {
|
|
||||||
return (
|
|
||||||
<TableRowCell key={name}>
|
|
||||||
<TrackLanguage
|
|
||||||
language={language}
|
|
||||||
isCutoffMet={languageCutoffNotMet}
|
|
||||||
/>
|
|
||||||
</TableRowCell>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name === 'quality') {
|
if (name === 'quality') {
|
||||||
return (
|
return (
|
||||||
<TableRowCell key={name}>
|
<TableRowCell key={name}>
|
||||||
|
@ -232,8 +218,6 @@ HistoryRow.propTypes = {
|
||||||
artist: PropTypes.object.isRequired,
|
artist: PropTypes.object.isRequired,
|
||||||
album: PropTypes.object,
|
album: PropTypes.object,
|
||||||
track: PropTypes.object,
|
track: PropTypes.object,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
languageCutoffNotMet: PropTypes.bool.isRequired,
|
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
qualityCutoffNotMet: PropTypes.bool.isRequired,
|
qualityCutoffNotMet: PropTypes.bool.isRequired,
|
||||||
eventType: PropTypes.string.isRequired,
|
eventType: PropTypes.string.isRequired,
|
||||||
|
|
|
@ -12,7 +12,6 @@ import Icon from 'Components/Icon';
|
||||||
import Popover from 'Components/Tooltip/Popover';
|
import Popover from 'Components/Tooltip/Popover';
|
||||||
import ProtocolLabel from 'Activity/Queue/ProtocolLabel';
|
import ProtocolLabel from 'Activity/Queue/ProtocolLabel';
|
||||||
import AlbumTitleLink from 'Album/AlbumTitleLink';
|
import AlbumTitleLink from 'Album/AlbumTitleLink';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import InteractiveImportModal from 'InteractiveImport/InteractiveImportModal';
|
import InteractiveImportModal from 'InteractiveImport/InteractiveImportModal';
|
||||||
import ArtistNameLink from 'Artist/ArtistNameLink';
|
import ArtistNameLink from 'Artist/ArtistNameLink';
|
||||||
|
@ -73,7 +72,6 @@ class QueueRow extends Component {
|
||||||
errorMessage,
|
errorMessage,
|
||||||
artist,
|
artist,
|
||||||
album,
|
album,
|
||||||
language,
|
|
||||||
quality,
|
quality,
|
||||||
protocol,
|
protocol,
|
||||||
indexer,
|
indexer,
|
||||||
|
@ -185,16 +183,6 @@ class QueueRow extends Component {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name === 'language') {
|
|
||||||
return (
|
|
||||||
<TableRowCell key={name}>
|
|
||||||
<TrackLanguage
|
|
||||||
language={language}
|
|
||||||
/>
|
|
||||||
</TableRowCell>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name === 'quality') {
|
if (name === 'quality') {
|
||||||
return (
|
return (
|
||||||
<TableRowCell key={name}>
|
<TableRowCell key={name}>
|
||||||
|
@ -364,7 +352,6 @@ QueueRow.propTypes = {
|
||||||
errorMessage: PropTypes.string,
|
errorMessage: PropTypes.string,
|
||||||
artist: PropTypes.object,
|
artist: PropTypes.object,
|
||||||
album: PropTypes.object,
|
album: PropTypes.object,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
protocol: PropTypes.string.isRequired,
|
protocol: PropTypes.string.isRequired,
|
||||||
indexer: PropTypes.string,
|
indexer: PropTypes.string,
|
||||||
|
|
|
@ -58,7 +58,6 @@
|
||||||
composes: button from '~Components/Link/SpinnerButton.css';
|
composes: button from '~Components/Link/SpinnerButton.css';
|
||||||
}
|
}
|
||||||
|
|
||||||
.hideLanguageProfile,
|
|
||||||
.hideMetadataProfile {
|
.hideMetadataProfile {
|
||||||
composes: group from '~Components/Form/FormGroup.css';
|
composes: group from '~Components/Form/FormGroup.css';
|
||||||
|
|
||||||
|
|
|
@ -42,10 +42,6 @@ class AddNewArtistModalContent extends Component {
|
||||||
this.props.onInputChange({ name: 'qualityProfileId', value: parseInt(value) });
|
this.props.onInputChange({ name: 'qualityProfileId', value: parseInt(value) });
|
||||||
}
|
}
|
||||||
|
|
||||||
onLanguageProfileIdChange = ({ value }) => {
|
|
||||||
this.props.onInputChange({ name: 'languageProfileId', value: parseInt(value) });
|
|
||||||
}
|
|
||||||
|
|
||||||
onMetadataProfileIdChange = ({ value }) => {
|
onMetadataProfileIdChange = ({ value }) => {
|
||||||
this.props.onInputChange({ name: 'metadataProfileId', value: parseInt(value) });
|
this.props.onInputChange({ name: 'metadataProfileId', value: parseInt(value) });
|
||||||
}
|
}
|
||||||
|
@ -66,11 +62,9 @@ class AddNewArtistModalContent extends Component {
|
||||||
rootFolderPath,
|
rootFolderPath,
|
||||||
monitor,
|
monitor,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
tags,
|
tags,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
isSmallScreen,
|
isSmallScreen,
|
||||||
onModalClose,
|
onModalClose,
|
||||||
|
@ -159,17 +153,6 @@ class AddNewArtistModalContent extends Component {
|
||||||
/>
|
/>
|
||||||
</FormGroup>
|
</FormGroup>
|
||||||
|
|
||||||
<FormGroup className={showLanguageProfile ? undefined : styles.hideLanguageProfile}>
|
|
||||||
<FormLabel>Language Profile</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.LANGUAGE_PROFILE_SELECT}
|
|
||||||
name="languageProfileId"
|
|
||||||
onChange={this.onLanguageProfileIdChange}
|
|
||||||
{...languageProfileId}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
|
|
||||||
<FormGroup className={showMetadataProfile ? undefined : styles.hideMetadataProfile}>
|
<FormGroup className={showMetadataProfile ? undefined : styles.hideMetadataProfile}>
|
||||||
<FormLabel>Metadata Profile</FormLabel>
|
<FormLabel>Metadata Profile</FormLabel>
|
||||||
|
|
||||||
|
@ -245,11 +228,9 @@ AddNewArtistModalContent.propTypes = {
|
||||||
rootFolderPath: PropTypes.object,
|
rootFolderPath: PropTypes.object,
|
||||||
monitor: PropTypes.object.isRequired,
|
monitor: PropTypes.object.isRequired,
|
||||||
qualityProfileId: PropTypes.object,
|
qualityProfileId: PropTypes.object,
|
||||||
languageProfileId: PropTypes.object,
|
|
||||||
metadataProfileId: PropTypes.object,
|
metadataProfileId: PropTypes.object,
|
||||||
albumFolder: PropTypes.object.isRequired,
|
albumFolder: PropTypes.object.isRequired,
|
||||||
tags: PropTypes.object.isRequired,
|
tags: PropTypes.object.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
isSmallScreen: PropTypes.bool.isRequired,
|
isSmallScreen: PropTypes.bool.isRequired,
|
||||||
onModalClose: PropTypes.func.isRequired,
|
onModalClose: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -10,10 +10,9 @@ import AddNewArtistModalContent from './AddNewArtistModalContent';
|
||||||
function createMapStateToProps() {
|
function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
(state) => state.addArtist,
|
(state) => state.addArtist,
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.metadataProfiles,
|
(state) => state.settings.metadataProfiles,
|
||||||
createDimensionsSelector(),
|
createDimensionsSelector(),
|
||||||
(addArtistState, languageProfiles, metadataProfiles, dimensions) => {
|
(addArtistState, metadataProfiles, dimensions) => {
|
||||||
const {
|
const {
|
||||||
isAdding,
|
isAdding,
|
||||||
addError,
|
addError,
|
||||||
|
@ -29,7 +28,6 @@ function createMapStateToProps() {
|
||||||
return {
|
return {
|
||||||
isAdding,
|
isAdding,
|
||||||
addError,
|
addError,
|
||||||
showLanguageProfile: languageProfiles.items.length > 1,
|
|
||||||
showMetadataProfile: metadataProfiles.items.length > 1,
|
showMetadataProfile: metadataProfiles.items.length > 1,
|
||||||
isSmallScreen: dimensions.isSmallScreen,
|
isSmallScreen: dimensions.isSmallScreen,
|
||||||
validationErrors,
|
validationErrors,
|
||||||
|
@ -60,7 +58,6 @@ class AddNewArtistModalContentConnector extends Component {
|
||||||
rootFolderPath,
|
rootFolderPath,
|
||||||
monitor,
|
monitor,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
tags
|
tags
|
||||||
|
@ -71,7 +68,6 @@ class AddNewArtistModalContentConnector extends Component {
|
||||||
rootFolderPath: rootFolderPath.value,
|
rootFolderPath: rootFolderPath.value,
|
||||||
monitor: monitor.value,
|
monitor: monitor.value,
|
||||||
qualityProfileId: qualityProfileId.value,
|
qualityProfileId: qualityProfileId.value,
|
||||||
languageProfileId: languageProfileId.value,
|
|
||||||
metadataProfileId: metadataProfileId.value,
|
metadataProfileId: metadataProfileId.value,
|
||||||
albumFolder: albumFolder.value,
|
albumFolder: albumFolder.value,
|
||||||
tags: tags.value,
|
tags: tags.value,
|
||||||
|
@ -98,7 +94,6 @@ AddNewArtistModalContentConnector.propTypes = {
|
||||||
rootFolderPath: PropTypes.object,
|
rootFolderPath: PropTypes.object,
|
||||||
monitor: PropTypes.object.isRequired,
|
monitor: PropTypes.object.isRequired,
|
||||||
qualityProfileId: PropTypes.object,
|
qualityProfileId: PropTypes.object,
|
||||||
languageProfileId: PropTypes.object,
|
|
||||||
metadataProfileId: PropTypes.object,
|
metadataProfileId: PropTypes.object,
|
||||||
albumFolder: PropTypes.object.isRequired,
|
albumFolder: PropTypes.object.isRequired,
|
||||||
tags: PropTypes.object.isRequired,
|
tags: PropTypes.object.isRequired,
|
||||||
|
|
|
@ -87,7 +87,6 @@ class ImportArtist extends Component {
|
||||||
rootFoldersPopulated,
|
rootFoldersPopulated,
|
||||||
rootFoldersError,
|
rootFoldersError,
|
||||||
unmappedFolders,
|
unmappedFolders,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile
|
showMetadataProfile
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
|
||||||
|
@ -130,7 +129,6 @@ class ImportArtist extends Component {
|
||||||
allUnselected={allUnselected}
|
allUnselected={allUnselected}
|
||||||
selectedState={selectedState}
|
selectedState={selectedState}
|
||||||
contentBody={contentBody}
|
contentBody={contentBody}
|
||||||
showLanguageProfile={showLanguageProfile}
|
|
||||||
showMetadataProfile={showMetadataProfile}
|
showMetadataProfile={showMetadataProfile}
|
||||||
scrollTop={this.state.scrollTop}
|
scrollTop={this.state.scrollTop}
|
||||||
onSelectAllChange={this.onSelectAllChange}
|
onSelectAllChange={this.onSelectAllChange}
|
||||||
|
@ -145,7 +143,6 @@ class ImportArtist extends Component {
|
||||||
!rootFoldersError && rootFoldersPopulated && !!unmappedFolders.length &&
|
!rootFoldersError && rootFoldersPopulated && !!unmappedFolders.length &&
|
||||||
<ImportArtistFooterConnector
|
<ImportArtistFooterConnector
|
||||||
selectedIds={this.getSelectedIds()}
|
selectedIds={this.getSelectedIds()}
|
||||||
showLanguageProfile={showLanguageProfile}
|
|
||||||
showMetadataProfile={showMetadataProfile}
|
showMetadataProfile={showMetadataProfile}
|
||||||
onInputChange={this.onInputChange}
|
onInputChange={this.onInputChange}
|
||||||
onImportPress={this.onImportPress}
|
onImportPress={this.onImportPress}
|
||||||
|
@ -164,7 +161,6 @@ ImportArtist.propTypes = {
|
||||||
rootFoldersError: PropTypes.object,
|
rootFoldersError: PropTypes.object,
|
||||||
unmappedFolders: PropTypes.arrayOf(PropTypes.object),
|
unmappedFolders: PropTypes.arrayOf(PropTypes.object),
|
||||||
items: PropTypes.arrayOf(PropTypes.object),
|
items: PropTypes.arrayOf(PropTypes.object),
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
onInputChange: PropTypes.func.isRequired,
|
onInputChange: PropTypes.func.isRequired,
|
||||||
onImportPress: PropTypes.func.isRequired
|
onImportPress: PropTypes.func.isRequired
|
||||||
|
|
|
@ -17,7 +17,6 @@ function createMapStateToProps() {
|
||||||
(state) => state.addArtist,
|
(state) => state.addArtist,
|
||||||
(state) => state.importArtist,
|
(state) => state.importArtist,
|
||||||
(state) => state.settings.qualityProfiles,
|
(state) => state.settings.qualityProfiles,
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.metadataProfiles,
|
(state) => state.settings.metadataProfiles,
|
||||||
(
|
(
|
||||||
match,
|
match,
|
||||||
|
@ -25,7 +24,6 @@ function createMapStateToProps() {
|
||||||
addArtist,
|
addArtist,
|
||||||
importArtistState,
|
importArtistState,
|
||||||
qualityProfiles,
|
qualityProfiles,
|
||||||
languageProfiles,
|
|
||||||
metadataProfiles
|
metadataProfiles
|
||||||
) => {
|
) => {
|
||||||
const {
|
const {
|
||||||
|
@ -43,12 +41,9 @@ function createMapStateToProps() {
|
||||||
rootFoldersPopulated,
|
rootFoldersPopulated,
|
||||||
rootFoldersError,
|
rootFoldersError,
|
||||||
qualityProfiles: qualityProfiles.items,
|
qualityProfiles: qualityProfiles.items,
|
||||||
languageProfiles: languageProfiles.items,
|
|
||||||
metadataProfiles: metadataProfiles.items,
|
metadataProfiles: metadataProfiles.items,
|
||||||
showLanguageProfile: languageProfiles.items.length > 1,
|
|
||||||
showMetadataProfile: metadataProfiles.items.length > 1,
|
showMetadataProfile: metadataProfiles.items.length > 1,
|
||||||
defaultQualityProfileId: addArtist.defaults.qualityProfileId,
|
defaultQualityProfileId: addArtist.defaults.qualityProfileId,
|
||||||
defaultLanguageProfileId: addArtist.defaults.languageProfileId,
|
|
||||||
defaultMetadataProfileId: addArtist.defaults.metadataProfileId
|
defaultMetadataProfileId: addArtist.defaults.metadataProfileId
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -83,10 +78,8 @@ class ImportArtistConnector extends Component {
|
||||||
componentDidMount() {
|
componentDidMount() {
|
||||||
const {
|
const {
|
||||||
qualityProfiles,
|
qualityProfiles,
|
||||||
languageProfiles,
|
|
||||||
metadataProfiles,
|
metadataProfiles,
|
||||||
defaultQualityProfileId,
|
defaultQualityProfileId,
|
||||||
defaultLanguageProfileId,
|
|
||||||
defaultMetadataProfileId,
|
defaultMetadataProfileId,
|
||||||
dispatchFetchRootFolders,
|
dispatchFetchRootFolders,
|
||||||
dispatchSetAddArtistDefault
|
dispatchSetAddArtistDefault
|
||||||
|
@ -107,14 +100,6 @@ class ImportArtistConnector extends Component {
|
||||||
setDefaultPayload.qualityProfileId = qualityProfiles[0].id;
|
setDefaultPayload.qualityProfileId = qualityProfiles[0].id;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (
|
|
||||||
!defaultLanguageProfileId ||
|
|
||||||
!languageProfiles.some((p) => p.id === defaultLanguageProfileId)
|
|
||||||
) {
|
|
||||||
setDefaults = true;
|
|
||||||
setDefaultPayload.languageProfileId = languageProfiles[0].id;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (
|
if (
|
||||||
!defaultMetadataProfileId ||
|
!defaultMetadataProfileId ||
|
||||||
!metadataProfiles.some((p) => p.id === defaultMetadataProfileId)
|
!metadataProfiles.some((p) => p.id === defaultMetadataProfileId)
|
||||||
|
@ -172,10 +157,8 @@ ImportArtistConnector.propTypes = {
|
||||||
match: routeMatchShape.isRequired,
|
match: routeMatchShape.isRequired,
|
||||||
rootFoldersPopulated: PropTypes.bool.isRequired,
|
rootFoldersPopulated: PropTypes.bool.isRequired,
|
||||||
qualityProfiles: PropTypes.arrayOf(PropTypes.object).isRequired,
|
qualityProfiles: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
languageProfiles: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
metadataProfiles: PropTypes.arrayOf(PropTypes.object).isRequired,
|
metadataProfiles: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
defaultQualityProfileId: PropTypes.number.isRequired,
|
defaultQualityProfileId: PropTypes.number.isRequired,
|
||||||
defaultLanguageProfileId: PropTypes.number.isRequired,
|
|
||||||
defaultMetadataProfileId: PropTypes.number.isRequired,
|
defaultMetadataProfileId: PropTypes.number.isRequired,
|
||||||
dispatchSetImportArtistValue: PropTypes.func.isRequired,
|
dispatchSetImportArtistValue: PropTypes.func.isRequired,
|
||||||
dispatchImportArtist: PropTypes.func.isRequired,
|
dispatchImportArtist: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -23,7 +23,6 @@ class ImportArtistFooter extends Component {
|
||||||
const {
|
const {
|
||||||
defaultMonitor,
|
defaultMonitor,
|
||||||
defaultQualityProfileId,
|
defaultQualityProfileId,
|
||||||
defaultLanguageProfileId,
|
|
||||||
defaultMetadataProfileId,
|
defaultMetadataProfileId,
|
||||||
defaultAlbumFolder
|
defaultAlbumFolder
|
||||||
} = props;
|
} = props;
|
||||||
|
@ -31,7 +30,6 @@ class ImportArtistFooter extends Component {
|
||||||
this.state = {
|
this.state = {
|
||||||
monitor: defaultMonitor,
|
monitor: defaultMonitor,
|
||||||
qualityProfileId: defaultQualityProfileId,
|
qualityProfileId: defaultQualityProfileId,
|
||||||
languageProfileId: defaultLanguageProfileId,
|
|
||||||
metadataProfileId: defaultMetadataProfileId,
|
metadataProfileId: defaultMetadataProfileId,
|
||||||
albumFolder: defaultAlbumFolder
|
albumFolder: defaultAlbumFolder
|
||||||
};
|
};
|
||||||
|
@ -41,12 +39,10 @@ class ImportArtistFooter extends Component {
|
||||||
const {
|
const {
|
||||||
defaultMonitor,
|
defaultMonitor,
|
||||||
defaultQualityProfileId,
|
defaultQualityProfileId,
|
||||||
defaultLanguageProfileId,
|
|
||||||
defaultMetadataProfileId,
|
defaultMetadataProfileId,
|
||||||
defaultAlbumFolder,
|
defaultAlbumFolder,
|
||||||
isMonitorMixed,
|
isMonitorMixed,
|
||||||
isQualityProfileIdMixed,
|
isQualityProfileIdMixed,
|
||||||
isLanguageProfileIdMixed,
|
|
||||||
isMetadataProfileIdMixed,
|
isMetadataProfileIdMixed,
|
||||||
isAlbumFolderMixed
|
isAlbumFolderMixed
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
@ -54,7 +50,6 @@ class ImportArtistFooter extends Component {
|
||||||
const {
|
const {
|
||||||
monitor,
|
monitor,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder
|
albumFolder
|
||||||
} = this.state;
|
} = this.state;
|
||||||
|
@ -73,12 +68,6 @@ class ImportArtistFooter extends Component {
|
||||||
newState.qualityProfileId = defaultQualityProfileId;
|
newState.qualityProfileId = defaultQualityProfileId;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isLanguageProfileIdMixed && languageProfileId !== MIXED) {
|
|
||||||
newState.languageProfileId = MIXED;
|
|
||||||
} else if (!isLanguageProfileIdMixed && languageProfileId !== defaultLanguageProfileId) {
|
|
||||||
newState.languageProfileId = defaultLanguageProfileId;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isMetadataProfileIdMixed && metadataProfileId !== MIXED) {
|
if (isMetadataProfileIdMixed && metadataProfileId !== MIXED) {
|
||||||
newState.metadataProfileId = MIXED;
|
newState.metadataProfileId = MIXED;
|
||||||
} else if (!isMetadataProfileIdMixed && metadataProfileId !== defaultMetadataProfileId) {
|
} else if (!isMetadataProfileIdMixed && metadataProfileId !== defaultMetadataProfileId) {
|
||||||
|
@ -114,10 +103,8 @@ class ImportArtistFooter extends Component {
|
||||||
isLookingUpArtist,
|
isLookingUpArtist,
|
||||||
isMonitorMixed,
|
isMonitorMixed,
|
||||||
isQualityProfileIdMixed,
|
isQualityProfileIdMixed,
|
||||||
isLanguageProfileIdMixed,
|
|
||||||
isMetadataProfileIdMixed,
|
isMetadataProfileIdMixed,
|
||||||
hasUnsearchedItems,
|
hasUnsearchedItems,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
onImportPress,
|
onImportPress,
|
||||||
onLookupPress,
|
onLookupPress,
|
||||||
|
@ -127,7 +114,6 @@ class ImportArtistFooter extends Component {
|
||||||
const {
|
const {
|
||||||
monitor,
|
monitor,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder
|
albumFolder
|
||||||
} = this.state;
|
} = this.state;
|
||||||
|
@ -164,24 +150,6 @@ class ImportArtistFooter extends Component {
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{
|
|
||||||
showLanguageProfile &&
|
|
||||||
<div className={styles.inputContainer}>
|
|
||||||
<div className={styles.label}>
|
|
||||||
Language Profile
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.LANGUAGE_PROFILE_SELECT}
|
|
||||||
name="languageProfileId"
|
|
||||||
value={languageProfileId}
|
|
||||||
isDisabled={!selectedCount}
|
|
||||||
includeMixed={isLanguageProfileIdMixed}
|
|
||||||
onChange={this.onInputChange}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
{
|
||||||
showMetadataProfile &&
|
showMetadataProfile &&
|
||||||
<div className={styles.inputContainer}>
|
<div className={styles.inputContainer}>
|
||||||
|
@ -276,16 +244,13 @@ ImportArtistFooter.propTypes = {
|
||||||
isLookingUpArtist: PropTypes.bool.isRequired,
|
isLookingUpArtist: PropTypes.bool.isRequired,
|
||||||
defaultMonitor: PropTypes.string.isRequired,
|
defaultMonitor: PropTypes.string.isRequired,
|
||||||
defaultQualityProfileId: PropTypes.number,
|
defaultQualityProfileId: PropTypes.number,
|
||||||
defaultLanguageProfileId: PropTypes.number,
|
|
||||||
defaultMetadataProfileId: PropTypes.number,
|
defaultMetadataProfileId: PropTypes.number,
|
||||||
defaultAlbumFolder: PropTypes.bool.isRequired,
|
defaultAlbumFolder: PropTypes.bool.isRequired,
|
||||||
isMonitorMixed: PropTypes.bool.isRequired,
|
isMonitorMixed: PropTypes.bool.isRequired,
|
||||||
isQualityProfileIdMixed: PropTypes.bool.isRequired,
|
isQualityProfileIdMixed: PropTypes.bool.isRequired,
|
||||||
isLanguageProfileIdMixed: PropTypes.bool.isRequired,
|
|
||||||
isMetadataProfileIdMixed: PropTypes.bool.isRequired,
|
isMetadataProfileIdMixed: PropTypes.bool.isRequired,
|
||||||
isAlbumFolderMixed: PropTypes.bool.isRequired,
|
isAlbumFolderMixed: PropTypes.bool.isRequired,
|
||||||
hasUnsearchedItems: PropTypes.bool.isRequired,
|
hasUnsearchedItems: PropTypes.bool.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
onInputChange: PropTypes.func.isRequired,
|
onInputChange: PropTypes.func.isRequired,
|
||||||
onImportPress: PropTypes.func.isRequired,
|
onImportPress: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -19,7 +19,6 @@ function createMapStateToProps() {
|
||||||
const {
|
const {
|
||||||
monitor: defaultMonitor,
|
monitor: defaultMonitor,
|
||||||
qualityProfileId: defaultQualityProfileId,
|
qualityProfileId: defaultQualityProfileId,
|
||||||
languageProfileId: defaultLanguageProfileId,
|
|
||||||
metadataProfileId: defaultMetadataProfileId,
|
metadataProfileId: defaultMetadataProfileId,
|
||||||
albumFolder: defaultAlbumFolder
|
albumFolder: defaultAlbumFolder
|
||||||
} = addArtist.defaults;
|
} = addArtist.defaults;
|
||||||
|
@ -32,7 +31,6 @@ function createMapStateToProps() {
|
||||||
|
|
||||||
const isMonitorMixed = isMixed(items, selectedIds, defaultMonitor, 'monitor');
|
const isMonitorMixed = isMixed(items, selectedIds, defaultMonitor, 'monitor');
|
||||||
const isQualityProfileIdMixed = isMixed(items, selectedIds, defaultQualityProfileId, 'qualityProfileId');
|
const isQualityProfileIdMixed = isMixed(items, selectedIds, defaultQualityProfileId, 'qualityProfileId');
|
||||||
const isLanguageProfileIdMixed = isMixed(items, selectedIds, defaultLanguageProfileId, 'languageProfileId');
|
|
||||||
const isMetadataProfileIdMixed = isMixed(items, selectedIds, defaultMetadataProfileId, 'metadataProfileId');
|
const isMetadataProfileIdMixed = isMixed(items, selectedIds, defaultMetadataProfileId, 'metadataProfileId');
|
||||||
const isAlbumFolderMixed = isMixed(items, selectedIds, defaultAlbumFolder, 'albumFolder');
|
const isAlbumFolderMixed = isMixed(items, selectedIds, defaultAlbumFolder, 'albumFolder');
|
||||||
const hasUnsearchedItems = !isLookingUpArtist && items.some((item) => !item.isPopulated);
|
const hasUnsearchedItems = !isLookingUpArtist && items.some((item) => !item.isPopulated);
|
||||||
|
@ -43,12 +41,10 @@ function createMapStateToProps() {
|
||||||
isImporting,
|
isImporting,
|
||||||
defaultMonitor,
|
defaultMonitor,
|
||||||
defaultQualityProfileId,
|
defaultQualityProfileId,
|
||||||
defaultLanguageProfileId,
|
|
||||||
defaultMetadataProfileId,
|
defaultMetadataProfileId,
|
||||||
defaultAlbumFolder,
|
defaultAlbumFolder,
|
||||||
isMonitorMixed,
|
isMonitorMixed,
|
||||||
isQualityProfileIdMixed,
|
isQualityProfileIdMixed,
|
||||||
isLanguageProfileIdMixed,
|
|
||||||
isMetadataProfileIdMixed,
|
isMetadataProfileIdMixed,
|
||||||
isAlbumFolderMixed,
|
isAlbumFolderMixed,
|
||||||
hasUnsearchedItems
|
hasUnsearchedItems
|
||||||
|
|
|
@ -12,7 +12,6 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.qualityProfile,
|
.qualityProfile,
|
||||||
.languageProfile,
|
|
||||||
.metadataProfile {
|
.metadataProfile {
|
||||||
composes: headerCell from '~Components/Table/VirtualTableHeaderCell.css';
|
composes: headerCell from '~Components/Table/VirtualTableHeaderCell.css';
|
||||||
|
|
||||||
|
|
|
@ -12,7 +12,6 @@ import styles from './ImportArtistHeader.css';
|
||||||
|
|
||||||
function ImportArtistHeader(props) {
|
function ImportArtistHeader(props) {
|
||||||
const {
|
const {
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
allSelected,
|
allSelected,
|
||||||
allUnselected,
|
allUnselected,
|
||||||
|
@ -60,16 +59,6 @@ function ImportArtistHeader(props) {
|
||||||
Quality Profile
|
Quality Profile
|
||||||
</VirtualTableHeaderCell>
|
</VirtualTableHeaderCell>
|
||||||
|
|
||||||
{
|
|
||||||
showLanguageProfile &&
|
|
||||||
<VirtualTableHeaderCell
|
|
||||||
className={styles.languageProfile}
|
|
||||||
name="languageProfileId"
|
|
||||||
>
|
|
||||||
Language Profile
|
|
||||||
</VirtualTableHeaderCell>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
{
|
||||||
showMetadataProfile &&
|
showMetadataProfile &&
|
||||||
<VirtualTableHeaderCell
|
<VirtualTableHeaderCell
|
||||||
|
@ -98,7 +87,6 @@ function ImportArtistHeader(props) {
|
||||||
}
|
}
|
||||||
|
|
||||||
ImportArtistHeader.propTypes = {
|
ImportArtistHeader.propTypes = {
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
allSelected: PropTypes.bool.isRequired,
|
allSelected: PropTypes.bool.isRequired,
|
||||||
allUnselected: PropTypes.bool.isRequired,
|
allUnselected: PropTypes.bool.isRequired,
|
||||||
|
|
|
@ -17,7 +17,6 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.qualityProfile,
|
.qualityProfile,
|
||||||
.languageProfile,
|
|
||||||
.metadataProfile {
|
.metadataProfile {
|
||||||
composes: cell from '~Components/Table/Cells/VirtualTableRowCell.css';
|
composes: cell from '~Components/Table/Cells/VirtualTableRowCell.css';
|
||||||
|
|
||||||
|
@ -39,7 +38,6 @@
|
||||||
min-width: 300px;
|
min-width: 300px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.hideLanguageProfile,
|
|
||||||
.hideMetadataProfile {
|
.hideMetadataProfile {
|
||||||
composes: cell from '~Components/Table/Cells/VirtualTableRowCell.css';
|
composes: cell from '~Components/Table/Cells/VirtualTableRowCell.css';
|
||||||
|
|
||||||
|
|
|
@ -14,12 +14,10 @@ function ImportArtistRow(props) {
|
||||||
id,
|
id,
|
||||||
monitor,
|
monitor,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
selectedArtist,
|
selectedArtist,
|
||||||
isExistingArtist,
|
isExistingArtist,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
isSelected,
|
isSelected,
|
||||||
onSelectedChange,
|
onSelectedChange,
|
||||||
|
@ -58,17 +56,6 @@ function ImportArtistRow(props) {
|
||||||
/>
|
/>
|
||||||
</VirtualTableRowCell>
|
</VirtualTableRowCell>
|
||||||
|
|
||||||
<VirtualTableRowCell
|
|
||||||
className={showLanguageProfile ? styles.languageProfile : styles.hideLanguageProfile}
|
|
||||||
>
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.LANGUAGE_PROFILE_SELECT}
|
|
||||||
name="languageProfileId"
|
|
||||||
value={languageProfileId}
|
|
||||||
onChange={onInputChange}
|
|
||||||
/>
|
|
||||||
</VirtualTableRowCell>
|
|
||||||
|
|
||||||
<VirtualTableRowCell
|
<VirtualTableRowCell
|
||||||
className={showMetadataProfile ? styles.metadataProfile : styles.hideMetadataProfile}
|
className={showMetadataProfile ? styles.metadataProfile : styles.hideMetadataProfile}
|
||||||
>
|
>
|
||||||
|
@ -104,13 +91,11 @@ ImportArtistRow.propTypes = {
|
||||||
id: PropTypes.string.isRequired,
|
id: PropTypes.string.isRequired,
|
||||||
monitor: PropTypes.string.isRequired,
|
monitor: PropTypes.string.isRequired,
|
||||||
qualityProfileId: PropTypes.number.isRequired,
|
qualityProfileId: PropTypes.number.isRequired,
|
||||||
languageProfileId: PropTypes.number.isRequired,
|
|
||||||
metadataProfileId: PropTypes.number.isRequired,
|
metadataProfileId: PropTypes.number.isRequired,
|
||||||
albumFolder: PropTypes.bool.isRequired,
|
albumFolder: PropTypes.bool.isRequired,
|
||||||
selectedArtist: PropTypes.object,
|
selectedArtist: PropTypes.object,
|
||||||
isExistingArtist: PropTypes.bool.isRequired,
|
isExistingArtist: PropTypes.bool.isRequired,
|
||||||
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
isSelected: PropTypes.bool,
|
isSelected: PropTypes.bool,
|
||||||
onSelectedChange: PropTypes.func.isRequired,
|
onSelectedChange: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -15,7 +15,6 @@ class ImportArtistTable extends Component {
|
||||||
unmappedFolders,
|
unmappedFolders,
|
||||||
defaultMonitor,
|
defaultMonitor,
|
||||||
defaultQualityProfileId,
|
defaultQualityProfileId,
|
||||||
defaultLanguageProfileId,
|
|
||||||
defaultMetadataProfileId,
|
defaultMetadataProfileId,
|
||||||
defaultAlbumFolder,
|
defaultAlbumFolder,
|
||||||
onArtistLookup,
|
onArtistLookup,
|
||||||
|
@ -25,7 +24,6 @@ class ImportArtistTable extends Component {
|
||||||
const values = {
|
const values = {
|
||||||
monitor: defaultMonitor,
|
monitor: defaultMonitor,
|
||||||
qualityProfileId: defaultQualityProfileId,
|
qualityProfileId: defaultQualityProfileId,
|
||||||
languageProfileId: defaultLanguageProfileId,
|
|
||||||
metadataProfileId: defaultMetadataProfileId,
|
metadataProfileId: defaultMetadataProfileId,
|
||||||
albumFolder: defaultAlbumFolder
|
albumFolder: defaultAlbumFolder
|
||||||
};
|
};
|
||||||
|
@ -105,7 +103,6 @@ class ImportArtistTable extends Component {
|
||||||
rootFolderId,
|
rootFolderId,
|
||||||
items,
|
items,
|
||||||
selectedState,
|
selectedState,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
onSelectedChange
|
onSelectedChange
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
@ -117,7 +114,6 @@ class ImportArtistTable extends Component {
|
||||||
key={key}
|
key={key}
|
||||||
style={style}
|
style={style}
|
||||||
rootFolderId={rootFolderId}
|
rootFolderId={rootFolderId}
|
||||||
showLanguageProfile={showLanguageProfile}
|
|
||||||
showMetadataProfile={showMetadataProfile}
|
showMetadataProfile={showMetadataProfile}
|
||||||
isSelected={selectedState[item.id]}
|
isSelected={selectedState[item.id]}
|
||||||
onSelectedChange={onSelectedChange}
|
onSelectedChange={onSelectedChange}
|
||||||
|
@ -136,7 +132,6 @@ class ImportArtistTable extends Component {
|
||||||
allUnselected,
|
allUnselected,
|
||||||
isSmallScreen,
|
isSmallScreen,
|
||||||
contentBody,
|
contentBody,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
scrollTop,
|
scrollTop,
|
||||||
selectedState,
|
selectedState,
|
||||||
|
@ -159,7 +154,6 @@ class ImportArtistTable extends Component {
|
||||||
rowRenderer={this.rowRenderer}
|
rowRenderer={this.rowRenderer}
|
||||||
header={
|
header={
|
||||||
<ImportArtistHeader
|
<ImportArtistHeader
|
||||||
showLanguageProfile={showLanguageProfile}
|
|
||||||
showMetadataProfile={showMetadataProfile}
|
showMetadataProfile={showMetadataProfile}
|
||||||
allSelected={allSelected}
|
allSelected={allSelected}
|
||||||
allUnselected={allUnselected}
|
allUnselected={allUnselected}
|
||||||
|
@ -179,7 +173,6 @@ ImportArtistTable.propTypes = {
|
||||||
unmappedFolders: PropTypes.arrayOf(PropTypes.object),
|
unmappedFolders: PropTypes.arrayOf(PropTypes.object),
|
||||||
defaultMonitor: PropTypes.string.isRequired,
|
defaultMonitor: PropTypes.string.isRequired,
|
||||||
defaultQualityProfileId: PropTypes.number,
|
defaultQualityProfileId: PropTypes.number,
|
||||||
defaultLanguageProfileId: PropTypes.number,
|
|
||||||
defaultMetadataProfileId: PropTypes.number,
|
defaultMetadataProfileId: PropTypes.number,
|
||||||
defaultAlbumFolder: PropTypes.bool.isRequired,
|
defaultAlbumFolder: PropTypes.bool.isRequired,
|
||||||
allSelected: PropTypes.bool.isRequired,
|
allSelected: PropTypes.bool.isRequired,
|
||||||
|
@ -188,7 +181,6 @@ ImportArtistTable.propTypes = {
|
||||||
isSmallScreen: PropTypes.bool.isRequired,
|
isSmallScreen: PropTypes.bool.isRequired,
|
||||||
allArtists: PropTypes.arrayOf(PropTypes.object),
|
allArtists: PropTypes.arrayOf(PropTypes.object),
|
||||||
contentBody: PropTypes.object.isRequired,
|
contentBody: PropTypes.object.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
scrollTop: PropTypes.number.isRequired,
|
scrollTop: PropTypes.number.isRequired,
|
||||||
onSelectAllChange: PropTypes.func.isRequired,
|
onSelectAllChange: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -14,7 +14,6 @@ function createMapStateToProps() {
|
||||||
return {
|
return {
|
||||||
defaultMonitor: addArtist.defaults.monitor,
|
defaultMonitor: addArtist.defaults.monitor,
|
||||||
defaultQualityProfileId: addArtist.defaults.qualityProfileId,
|
defaultQualityProfileId: addArtist.defaults.qualityProfileId,
|
||||||
defaultLanguageProfileId: addArtist.defaults.languageProfileId,
|
|
||||||
defaultMetadataProfileId: addArtist.defaults.metadataProfileId,
|
defaultMetadataProfileId: addArtist.defaults.metadataProfileId,
|
||||||
defaultAlbumFolder: addArtist.defaults.albumFolder,
|
defaultAlbumFolder: addArtist.defaults.albumFolder,
|
||||||
items: importArtist.items,
|
items: importArtist.items,
|
||||||
|
|
|
@ -22,7 +22,6 @@
|
||||||
width: 250px;
|
width: 250px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.language,
|
|
||||||
.duration,
|
.duration,
|
||||||
.status {
|
.status {
|
||||||
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
||||||
|
|
|
@ -4,7 +4,6 @@ import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import formatTimeSpan from 'Utilities/Date/formatTimeSpan';
|
import formatTimeSpan from 'Utilities/Date/formatTimeSpan';
|
||||||
import EpisodeStatusConnector from 'Album/EpisodeStatusConnector';
|
import EpisodeStatusConnector from 'Album/EpisodeStatusConnector';
|
||||||
import TrackFileLanguageConnector from 'TrackFile/TrackFileLanguageConnector';
|
|
||||||
import MediaInfoConnector from 'TrackFile/MediaInfoConnector';
|
import MediaInfoConnector from 'TrackFile/MediaInfoConnector';
|
||||||
import TrackActionsCell from './TrackActionsCell';
|
import TrackActionsCell from './TrackActionsCell';
|
||||||
import * as mediaInfoTypes from 'TrackFile/mediaInfoTypes';
|
import * as mediaInfoTypes from 'TrackFile/mediaInfoTypes';
|
||||||
|
@ -127,19 +126,6 @@ class TrackRow extends Component {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name === 'language') {
|
|
||||||
return (
|
|
||||||
<TableRowCell
|
|
||||||
key={name}
|
|
||||||
className={styles.language}
|
|
||||||
>
|
|
||||||
<TrackFileLanguageConnector
|
|
||||||
episodeFileId={trackFileId}
|
|
||||||
/>
|
|
||||||
</TableRowCell>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name === 'audioInfo') {
|
if (name === 'audioInfo') {
|
||||||
return (
|
return (
|
||||||
<TableRowCell
|
<TableRowCell
|
||||||
|
|
|
@ -1,37 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React from 'react';
|
|
||||||
import Label from 'Components/Label';
|
|
||||||
import { kinds } from 'Helpers/Props';
|
|
||||||
|
|
||||||
function TrackLanguage(props) {
|
|
||||||
const {
|
|
||||||
className,
|
|
||||||
language,
|
|
||||||
isCutoffNotMet
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
if (!language) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Label
|
|
||||||
className={className}
|
|
||||||
kind={isCutoffNotMet ? kinds.INVERSE : kinds.DEFAULT}
|
|
||||||
>
|
|
||||||
{language.name}
|
|
||||||
</Label>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
TrackLanguage.propTypes = {
|
|
||||||
className: PropTypes.string,
|
|
||||||
language: PropTypes.object,
|
|
||||||
isCutoffNotMet: PropTypes.bool
|
|
||||||
};
|
|
||||||
|
|
||||||
TrackLanguage.defaultProps = {
|
|
||||||
isCutoffNotMet: true
|
|
||||||
};
|
|
||||||
|
|
||||||
export default TrackLanguage;
|
|
|
@ -59,7 +59,6 @@ class EditArtistModalContent extends Component {
|
||||||
artistName,
|
artistName,
|
||||||
item,
|
item,
|
||||||
isSaving,
|
isSaving,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
originalPath,
|
originalPath,
|
||||||
onInputChange,
|
onInputChange,
|
||||||
|
@ -72,7 +71,6 @@ class EditArtistModalContent extends Component {
|
||||||
monitored,
|
monitored,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
path,
|
path,
|
||||||
tags
|
tags
|
||||||
|
@ -121,20 +119,6 @@ class EditArtistModalContent extends Component {
|
||||||
/>
|
/>
|
||||||
</FormGroup>
|
</FormGroup>
|
||||||
|
|
||||||
{
|
|
||||||
showLanguageProfile &&
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>Language Profile</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.LANGUAGE_PROFILE_SELECT}
|
|
||||||
name="languageProfileId"
|
|
||||||
{...languageProfileId}
|
|
||||||
onChange={onInputChange}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
{
|
||||||
showMetadataProfile &&
|
showMetadataProfile &&
|
||||||
<FormGroup>
|
<FormGroup>
|
||||||
|
@ -214,7 +198,6 @@ EditArtistModalContent.propTypes = {
|
||||||
artistName: PropTypes.string.isRequired,
|
artistName: PropTypes.string.isRequired,
|
||||||
item: PropTypes.object.isRequired,
|
item: PropTypes.object.isRequired,
|
||||||
isSaving: PropTypes.bool.isRequired,
|
isSaving: PropTypes.bool.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
isPathChanging: PropTypes.bool.isRequired,
|
isPathChanging: PropTypes.bool.isRequired,
|
||||||
originalPath: PropTypes.string.isRequired,
|
originalPath: PropTypes.string.isRequired,
|
||||||
|
|
|
@ -27,11 +27,10 @@ function createIsPathChangingSelector() {
|
||||||
function createMapStateToProps() {
|
function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
(state) => state.artist,
|
(state) => state.artist,
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.metadataProfiles,
|
(state) => state.settings.metadataProfiles,
|
||||||
createArtistSelector(),
|
createArtistSelector(),
|
||||||
createIsPathChangingSelector(),
|
createIsPathChangingSelector(),
|
||||||
(artistState, languageProfiles, metadataProfiles, artist, isPathChanging) => {
|
(artistState, metadataProfiles, artist, isPathChanging) => {
|
||||||
const {
|
const {
|
||||||
isSaving,
|
isSaving,
|
||||||
saveError,
|
saveError,
|
||||||
|
@ -42,7 +41,6 @@ function createMapStateToProps() {
|
||||||
'monitored',
|
'monitored',
|
||||||
'albumFolder',
|
'albumFolder',
|
||||||
'qualityProfileId',
|
'qualityProfileId',
|
||||||
'languageProfileId',
|
|
||||||
'metadataProfileId',
|
'metadataProfileId',
|
||||||
'path',
|
'path',
|
||||||
'tags'
|
'tags'
|
||||||
|
@ -57,7 +55,6 @@ function createMapStateToProps() {
|
||||||
isPathChanging,
|
isPathChanging,
|
||||||
originalPath: artist.path,
|
originalPath: artist.path,
|
||||||
item: settings.settings,
|
item: settings.settings,
|
||||||
showLanguageProfile: languageProfiles.items.length > 1,
|
|
||||||
showMetadataProfile: metadataProfiles.items.length > 1,
|
showMetadataProfile: metadataProfiles.items.length > 1,
|
||||||
...settings
|
...settings
|
||||||
};
|
};
|
||||||
|
|
|
@ -19,7 +19,7 @@ import ArtistEditorRowConnector from './ArtistEditorRowConnector';
|
||||||
import ArtistEditorFooter from './ArtistEditorFooter';
|
import ArtistEditorFooter from './ArtistEditorFooter';
|
||||||
import ArtistEditorFilterModalConnector from './ArtistEditorFilterModalConnector';
|
import ArtistEditorFilterModalConnector from './ArtistEditorFilterModalConnector';
|
||||||
|
|
||||||
function getColumns(showLanguageProfile, showMetadataProfile) {
|
function getColumns(showMetadataProfile) {
|
||||||
return [
|
return [
|
||||||
{
|
{
|
||||||
name: 'status',
|
name: 'status',
|
||||||
|
@ -38,12 +38,6 @@ function getColumns(showLanguageProfile, showMetadataProfile) {
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageProfileId',
|
|
||||||
label: 'Language Profile',
|
|
||||||
isSortable: true,
|
|
||||||
isVisible: showLanguageProfile
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'metadataProfileId',
|
name: 'metadataProfileId',
|
||||||
label: 'Metadata Profile',
|
label: 'Metadata Profile',
|
||||||
|
@ -86,7 +80,7 @@ class ArtistEditor extends Component {
|
||||||
selectedState: {},
|
selectedState: {},
|
||||||
isOrganizingArtistModalOpen: false,
|
isOrganizingArtistModalOpen: false,
|
||||||
isRetaggingArtistModalOpen: false,
|
isRetaggingArtistModalOpen: false,
|
||||||
columns: getColumns(props.showLanguageProfile, props.showMetadataProfile)
|
columns: getColumns(props.showMetadataProfile)
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -177,7 +171,6 @@ class ArtistEditor extends Component {
|
||||||
deleteError,
|
deleteError,
|
||||||
isOrganizingArtist,
|
isOrganizingArtist,
|
||||||
isRetaggingArtist,
|
isRetaggingArtist,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
onSortPress,
|
onSortPress,
|
||||||
onFilterSelect
|
onFilterSelect
|
||||||
|
@ -266,7 +259,6 @@ class ArtistEditor extends Component {
|
||||||
deleteError={deleteError}
|
deleteError={deleteError}
|
||||||
isOrganizingArtist={isOrganizingArtist}
|
isOrganizingArtist={isOrganizingArtist}
|
||||||
isRetaggingArtist={isRetaggingArtist}
|
isRetaggingArtist={isRetaggingArtist}
|
||||||
showLanguageProfile={showLanguageProfile}
|
|
||||||
showMetadataProfile={showMetadataProfile}
|
showMetadataProfile={showMetadataProfile}
|
||||||
onSaveSelected={this.onSaveSelected}
|
onSaveSelected={this.onSaveSelected}
|
||||||
onOrganizeArtistPress={this.onOrganizeArtistPress}
|
onOrganizeArtistPress={this.onOrganizeArtistPress}
|
||||||
|
@ -307,7 +299,6 @@ ArtistEditor.propTypes = {
|
||||||
deleteError: PropTypes.object,
|
deleteError: PropTypes.object,
|
||||||
isOrganizingArtist: PropTypes.bool.isRequired,
|
isOrganizingArtist: PropTypes.bool.isRequired,
|
||||||
isRetaggingArtist: PropTypes.bool.isRequired,
|
isRetaggingArtist: PropTypes.bool.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
onSortPress: PropTypes.func.isRequired,
|
onSortPress: PropTypes.func.isRequired,
|
||||||
onFilterSelect: PropTypes.func.isRequired,
|
onFilterSelect: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -12,16 +12,14 @@ import ArtistEditor from './ArtistEditor';
|
||||||
|
|
||||||
function createMapStateToProps() {
|
function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.metadataProfiles,
|
(state) => state.settings.metadataProfiles,
|
||||||
createClientSideCollectionSelector('artist', 'artistEditor'),
|
createClientSideCollectionSelector('artist', 'artistEditor'),
|
||||||
createCommandExecutingSelector(commandNames.RENAME_ARTIST),
|
createCommandExecutingSelector(commandNames.RENAME_ARTIST),
|
||||||
createCommandExecutingSelector(commandNames.RETAG_ARTIST),
|
createCommandExecutingSelector(commandNames.RETAG_ARTIST),
|
||||||
(languageProfiles, metadataProfiles, artist, isOrganizingArtist, isRetaggingArtist) => {
|
(metadataProfiles, artist, isOrganizingArtist, isRetaggingArtist) => {
|
||||||
return {
|
return {
|
||||||
isOrganizingArtist,
|
isOrganizingArtist,
|
||||||
isRetaggingArtist,
|
isRetaggingArtist,
|
||||||
showLanguageProfile: languageProfiles.items.length > 1,
|
|
||||||
showMetadataProfile: metadataProfiles.items.length > 1,
|
showMetadataProfile: metadataProfiles.items.length > 1,
|
||||||
...artist
|
...artist
|
||||||
};
|
};
|
||||||
|
|
|
@ -2,7 +2,6 @@ import PropTypes from 'prop-types';
|
||||||
import React, { Component } from 'react';
|
import React, { Component } from 'react';
|
||||||
import { kinds } from 'Helpers/Props';
|
import { kinds } from 'Helpers/Props';
|
||||||
import SelectInput from 'Components/Form/SelectInput';
|
import SelectInput from 'Components/Form/SelectInput';
|
||||||
import LanguageProfileSelectInputConnector from 'Components/Form/LanguageProfileSelectInputConnector';
|
|
||||||
import MetadataProfileSelectInputConnector from 'Components/Form/MetadataProfileSelectInputConnector';
|
import MetadataProfileSelectInputConnector from 'Components/Form/MetadataProfileSelectInputConnector';
|
||||||
import QualityProfileSelectInputConnector from 'Components/Form/QualityProfileSelectInputConnector';
|
import QualityProfileSelectInputConnector from 'Components/Form/QualityProfileSelectInputConnector';
|
||||||
import RootFolderSelectInputConnector from 'Components/Form/RootFolderSelectInputConnector';
|
import RootFolderSelectInputConnector from 'Components/Form/RootFolderSelectInputConnector';
|
||||||
|
@ -27,7 +26,6 @@ class ArtistEditorFooter extends Component {
|
||||||
this.state = {
|
this.state = {
|
||||||
monitored: NO_CHANGE,
|
monitored: NO_CHANGE,
|
||||||
qualityProfileId: NO_CHANGE,
|
qualityProfileId: NO_CHANGE,
|
||||||
languageProfileId: NO_CHANGE,
|
|
||||||
metadataProfileId: NO_CHANGE,
|
metadataProfileId: NO_CHANGE,
|
||||||
albumFolder: NO_CHANGE,
|
albumFolder: NO_CHANGE,
|
||||||
rootFolderPath: NO_CHANGE,
|
rootFolderPath: NO_CHANGE,
|
||||||
|
@ -49,7 +47,6 @@ class ArtistEditorFooter extends Component {
|
||||||
this.setState({
|
this.setState({
|
||||||
monitored: NO_CHANGE,
|
monitored: NO_CHANGE,
|
||||||
qualityProfileId: NO_CHANGE,
|
qualityProfileId: NO_CHANGE,
|
||||||
languageProfileId: NO_CHANGE,
|
|
||||||
metadataProfileId: NO_CHANGE,
|
metadataProfileId: NO_CHANGE,
|
||||||
albumFolder: NO_CHANGE,
|
albumFolder: NO_CHANGE,
|
||||||
rootFolderPath: NO_CHANGE,
|
rootFolderPath: NO_CHANGE,
|
||||||
|
@ -146,7 +143,6 @@ class ArtistEditorFooter extends Component {
|
||||||
isDeleting,
|
isDeleting,
|
||||||
isOrganizingArtist,
|
isOrganizingArtist,
|
||||||
isRetaggingArtist,
|
isRetaggingArtist,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
onOrganizeArtistPress,
|
onOrganizeArtistPress,
|
||||||
onRetagArtistPress
|
onRetagArtistPress
|
||||||
|
@ -155,7 +151,6 @@ class ArtistEditorFooter extends Component {
|
||||||
const {
|
const {
|
||||||
monitored,
|
monitored,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
rootFolderPath,
|
rootFolderPath,
|
||||||
|
@ -210,24 +205,6 @@ class ArtistEditorFooter extends Component {
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{
|
|
||||||
showLanguageProfile &&
|
|
||||||
<div className={styles.inputContainer}>
|
|
||||||
<ArtistEditorFooterLabel
|
|
||||||
label="Language Profile"
|
|
||||||
isSaving={isSaving && languageProfileId !== NO_CHANGE}
|
|
||||||
/>
|
|
||||||
|
|
||||||
<LanguageProfileSelectInputConnector
|
|
||||||
name="languageProfileId"
|
|
||||||
value={languageProfileId}
|
|
||||||
includeNoChange={true}
|
|
||||||
isDisabled={!selectedCount}
|
|
||||||
onChange={this.onInputChange}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
{
|
||||||
showMetadataProfile &&
|
showMetadataProfile &&
|
||||||
<div className={styles.inputContainer}>
|
<div className={styles.inputContainer}>
|
||||||
|
@ -363,7 +340,6 @@ ArtistEditorFooter.propTypes = {
|
||||||
deleteError: PropTypes.object,
|
deleteError: PropTypes.object,
|
||||||
isOrganizingArtist: PropTypes.bool.isRequired,
|
isOrganizingArtist: PropTypes.bool.isRequired,
|
||||||
isRetaggingArtist: PropTypes.bool.isRequired,
|
isRetaggingArtist: PropTypes.bool.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
onSaveSelected: PropTypes.func.isRequired,
|
onSaveSelected: PropTypes.func.isRequired,
|
||||||
onOrganizeArtistPress: PropTypes.func.isRequired,
|
onOrganizeArtistPress: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -31,7 +31,6 @@ class ArtistEditorRow extends Component {
|
||||||
artistName,
|
artistName,
|
||||||
artistType,
|
artistType,
|
||||||
monitored,
|
monitored,
|
||||||
languageProfile,
|
|
||||||
metadataProfile,
|
metadataProfile,
|
||||||
qualityProfile,
|
qualityProfile,
|
||||||
albumFolder,
|
albumFolder,
|
||||||
|
@ -67,13 +66,6 @@ class ArtistEditorRow extends Component {
|
||||||
{qualityProfile.name}
|
{qualityProfile.name}
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
|
||||||
{
|
|
||||||
_.find(columns, { name: 'languageProfileId' }).isVisible &&
|
|
||||||
<TableRowCell>
|
|
||||||
{languageProfile.name}
|
|
||||||
</TableRowCell>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
{
|
||||||
_.find(columns, { name: 'metadataProfileId' }).isVisible &&
|
_.find(columns, { name: 'metadataProfileId' }).isVisible &&
|
||||||
<TableRowCell>
|
<TableRowCell>
|
||||||
|
@ -111,7 +103,6 @@ ArtistEditorRow.propTypes = {
|
||||||
artistName: PropTypes.string.isRequired,
|
artistName: PropTypes.string.isRequired,
|
||||||
artistType: PropTypes.string.isRequired,
|
artistType: PropTypes.string.isRequired,
|
||||||
monitored: PropTypes.bool.isRequired,
|
monitored: PropTypes.bool.isRequired,
|
||||||
languageProfile: PropTypes.object.isRequired,
|
|
||||||
metadataProfile: PropTypes.object.isRequired,
|
metadataProfile: PropTypes.object.isRequired,
|
||||||
qualityProfile: PropTypes.object.isRequired,
|
qualityProfile: PropTypes.object.isRequired,
|
||||||
albumFolder: PropTypes.bool.isRequired,
|
albumFolder: PropTypes.bool.isRequired,
|
||||||
|
|
|
@ -2,19 +2,16 @@ import PropTypes from 'prop-types';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
import { createSelector } from 'reselect';
|
import { createSelector } from 'reselect';
|
||||||
import createLanguageProfileSelector from 'Store/Selectors/createLanguageProfileSelector';
|
|
||||||
import createMetadataProfileSelector from 'Store/Selectors/createMetadataProfileSelector';
|
import createMetadataProfileSelector from 'Store/Selectors/createMetadataProfileSelector';
|
||||||
import createQualityProfileSelector from 'Store/Selectors/createQualityProfileSelector';
|
import createQualityProfileSelector from 'Store/Selectors/createQualityProfileSelector';
|
||||||
import ArtistEditorRow from './ArtistEditorRow';
|
import ArtistEditorRow from './ArtistEditorRow';
|
||||||
|
|
||||||
function createMapStateToProps() {
|
function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
createLanguageProfileSelector(),
|
|
||||||
createMetadataProfileSelector(),
|
createMetadataProfileSelector(),
|
||||||
createQualityProfileSelector(),
|
createQualityProfileSelector(),
|
||||||
(languageProfile, metadataProfile, qualityProfile) => {
|
(metadataProfile, qualityProfile) => {
|
||||||
return {
|
return {
|
||||||
languageProfile,
|
|
||||||
metadataProfile,
|
metadataProfile,
|
||||||
qualityProfile
|
qualityProfile
|
||||||
};
|
};
|
||||||
|
|
|
@ -25,11 +25,6 @@ const columns = [
|
||||||
label: 'Source Title',
|
label: 'Source Title',
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: true
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'quality',
|
name: 'quality',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
|
|
@ -8,7 +8,6 @@ import RelativeDateCellConnector from 'Components/Table/Cells/RelativeDateCellCo
|
||||||
import TableRow from 'Components/Table/TableRow';
|
import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import Popover from 'Components/Tooltip/Popover';
|
import Popover from 'Components/Tooltip/Popover';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import HistoryDetailsConnector from 'Activity/History/Details/HistoryDetailsConnector';
|
import HistoryDetailsConnector from 'Activity/History/Details/HistoryDetailsConnector';
|
||||||
import HistoryEventTypeCell from 'Activity/History/HistoryEventTypeCell';
|
import HistoryEventTypeCell from 'Activity/History/HistoryEventTypeCell';
|
||||||
|
@ -73,8 +72,6 @@ class ArtistHistoryRow extends Component {
|
||||||
const {
|
const {
|
||||||
eventType,
|
eventType,
|
||||||
sourceTitle,
|
sourceTitle,
|
||||||
language,
|
|
||||||
languageCutoffNotMet,
|
|
||||||
quality,
|
quality,
|
||||||
qualityCutoffNotMet,
|
qualityCutoffNotMet,
|
||||||
date,
|
date,
|
||||||
|
@ -101,13 +98,6 @@ class ArtistHistoryRow extends Component {
|
||||||
{sourceTitle}
|
{sourceTitle}
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
|
||||||
<TableRowCell>
|
|
||||||
<TrackLanguage
|
|
||||||
language={language}
|
|
||||||
isCutoffNotMet={languageCutoffNotMet}
|
|
||||||
/>
|
|
||||||
</TableRowCell>
|
|
||||||
|
|
||||||
<TableRowCell>
|
<TableRowCell>
|
||||||
<TrackQuality
|
<TrackQuality
|
||||||
quality={quality}
|
quality={quality}
|
||||||
|
@ -167,8 +157,6 @@ ArtistHistoryRow.propTypes = {
|
||||||
id: PropTypes.number.isRequired,
|
id: PropTypes.number.isRequired,
|
||||||
eventType: PropTypes.string.isRequired,
|
eventType: PropTypes.string.isRequired,
|
||||||
sourceTitle: PropTypes.string.isRequired,
|
sourceTitle: PropTypes.string.isRequired,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
languageCutoffNotMet: PropTypes.bool.isRequired,
|
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
qualityCutoffNotMet: PropTypes.bool.isRequired,
|
qualityCutoffNotMet: PropTypes.bool.isRequired,
|
||||||
date: PropTypes.string.isRequired,
|
date: PropTypes.string.isRequired,
|
||||||
|
|
|
@ -7,7 +7,6 @@ import { createSelector } from 'reselect';
|
||||||
import createArtistSelector from 'Store/Selectors/createArtistSelector';
|
import createArtistSelector from 'Store/Selectors/createArtistSelector';
|
||||||
import createExecutingCommandsSelector from 'Store/Selectors/createExecutingCommandsSelector';
|
import createExecutingCommandsSelector from 'Store/Selectors/createExecutingCommandsSelector';
|
||||||
import createArtistQualityProfileSelector from 'Store/Selectors/createArtistQualityProfileSelector';
|
import createArtistQualityProfileSelector from 'Store/Selectors/createArtistQualityProfileSelector';
|
||||||
import createArtistLanguageProfileSelector from 'Store/Selectors/createArtistLanguageProfileSelector';
|
|
||||||
import createArtistMetadataProfileSelector from 'Store/Selectors/createArtistMetadataProfileSelector';
|
import createArtistMetadataProfileSelector from 'Store/Selectors/createArtistMetadataProfileSelector';
|
||||||
import { executeCommand } from 'Store/Actions/commandActions';
|
import { executeCommand } from 'Store/Actions/commandActions';
|
||||||
import * as commandNames from 'Commands/commandNames';
|
import * as commandNames from 'Commands/commandNames';
|
||||||
|
@ -36,14 +35,12 @@ function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
createArtistSelector(),
|
createArtistSelector(),
|
||||||
createArtistQualityProfileSelector(),
|
createArtistQualityProfileSelector(),
|
||||||
createArtistLanguageProfileSelector(),
|
|
||||||
createArtistMetadataProfileSelector(),
|
createArtistMetadataProfileSelector(),
|
||||||
selectShowSearchAction(),
|
selectShowSearchAction(),
|
||||||
createExecutingCommandsSelector(),
|
createExecutingCommandsSelector(),
|
||||||
(
|
(
|
||||||
artist,
|
artist,
|
||||||
qualityProfile,
|
qualityProfile,
|
||||||
languageProfile,
|
|
||||||
metadataProfile,
|
metadataProfile,
|
||||||
showSearchAction,
|
showSearchAction,
|
||||||
executingCommands
|
executingCommands
|
||||||
|
@ -77,7 +74,6 @@ function createMapStateToProps() {
|
||||||
return {
|
return {
|
||||||
...artist,
|
...artist,
|
||||||
qualityProfile,
|
qualityProfile,
|
||||||
languageProfile,
|
|
||||||
metadataProfile,
|
metadataProfile,
|
||||||
latestAlbum,
|
latestAlbum,
|
||||||
showSearchAction,
|
showSearchAction,
|
||||||
|
|
|
@ -234,7 +234,6 @@ class ArtistIndexBanners extends Component {
|
||||||
timeFormat={timeFormat}
|
timeFormat={timeFormat}
|
||||||
style={style}
|
style={style}
|
||||||
artistId={artist.id}
|
artistId={artist.id}
|
||||||
languageProfileId={artist.languageProfileId}
|
|
||||||
qualityProfileId={artist.qualityProfileId}
|
qualityProfileId={artist.qualityProfileId}
|
||||||
metadataProfileId={artist.metadataProfileId}
|
metadataProfileId={artist.metadataProfileId}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -55,15 +55,6 @@ function ArtistIndexSortMenu(props) {
|
||||||
Quality Profile
|
Quality Profile
|
||||||
</SortMenuItem>
|
</SortMenuItem>
|
||||||
|
|
||||||
<SortMenuItem
|
|
||||||
name="languageProfileId"
|
|
||||||
sortKey={sortKey}
|
|
||||||
sortDirection={sortDirection}
|
|
||||||
onPress={onSortSelect}
|
|
||||||
>
|
|
||||||
Language Profile
|
|
||||||
</SortMenuItem>
|
|
||||||
|
|
||||||
<SortMenuItem
|
<SortMenuItem
|
||||||
name="metadataProfileId"
|
name="metadataProfileId"
|
||||||
sortKey={sortKey}
|
sortKey={sortKey}
|
||||||
|
|
|
@ -200,7 +200,6 @@ class ArtistIndexOverviews extends Component {
|
||||||
isSmallScreen={isSmallScreen}
|
isSmallScreen={isSmallScreen}
|
||||||
style={style}
|
style={style}
|
||||||
artistId={artist.id}
|
artistId={artist.id}
|
||||||
languageProfileId={artist.languageProfileId}
|
|
||||||
qualityProfileId={artist.qualityProfileId}
|
qualityProfileId={artist.qualityProfileId}
|
||||||
metadataProfileId={artist.metadataProfileId}
|
metadataProfileId={artist.metadataProfileId}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -234,7 +234,6 @@ class ArtistIndexPosters extends Component {
|
||||||
timeFormat={timeFormat}
|
timeFormat={timeFormat}
|
||||||
style={style}
|
style={style}
|
||||||
artistId={artist.id}
|
artistId={artist.id}
|
||||||
languageProfileId={artist.languageProfileId}
|
|
||||||
qualityProfileId={artist.qualityProfileId}
|
qualityProfileId={artist.qualityProfileId}
|
||||||
metadataProfileId={artist.metadataProfileId}
|
metadataProfileId={artist.metadataProfileId}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -25,7 +25,6 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.qualityProfileId,
|
.qualityProfileId,
|
||||||
.languageProfileId,
|
|
||||||
.metadataProfileId {
|
.metadataProfileId {
|
||||||
composes: headerCell from '~Components/Table/VirtualTableHeaderCell.css';
|
composes: headerCell from '~Components/Table/VirtualTableHeaderCell.css';
|
||||||
|
|
||||||
|
|
|
@ -61,7 +61,6 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.qualityProfileId,
|
.qualityProfileId,
|
||||||
.languageProfileId,
|
|
||||||
.metadataProfileId {
|
.metadataProfileId {
|
||||||
composes: cell;
|
composes: cell;
|
||||||
|
|
||||||
|
|
|
@ -87,7 +87,6 @@ class ArtistIndexRow extends Component {
|
||||||
foreignArtistId,
|
foreignArtistId,
|
||||||
artistType,
|
artistType,
|
||||||
qualityProfile,
|
qualityProfile,
|
||||||
languageProfile,
|
|
||||||
metadataProfile,
|
metadataProfile,
|
||||||
nextAlbum,
|
nextAlbum,
|
||||||
lastAlbum,
|
lastAlbum,
|
||||||
|
@ -211,17 +210,6 @@ class ArtistIndexRow extends Component {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (name === 'languageProfileId') {
|
|
||||||
return (
|
|
||||||
<VirtualTableRowCell
|
|
||||||
key={name}
|
|
||||||
className={styles[name]}
|
|
||||||
>
|
|
||||||
{languageProfile.name}
|
|
||||||
</VirtualTableRowCell>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name === 'metadataProfileId') {
|
if (name === 'metadataProfileId') {
|
||||||
return (
|
return (
|
||||||
<VirtualTableRowCell
|
<VirtualTableRowCell
|
||||||
|
@ -462,7 +450,6 @@ ArtistIndexRow.propTypes = {
|
||||||
foreignArtistId: PropTypes.string.isRequired,
|
foreignArtistId: PropTypes.string.isRequired,
|
||||||
artistType: PropTypes.string,
|
artistType: PropTypes.string,
|
||||||
qualityProfile: PropTypes.object.isRequired,
|
qualityProfile: PropTypes.object.isRequired,
|
||||||
languageProfile: PropTypes.object.isRequired,
|
|
||||||
metadataProfile: PropTypes.object.isRequired,
|
metadataProfile: PropTypes.object.isRequired,
|
||||||
nextAlbum: PropTypes.object,
|
nextAlbum: PropTypes.object,
|
||||||
lastAlbum: PropTypes.object,
|
lastAlbum: PropTypes.object,
|
||||||
|
|
|
@ -56,7 +56,6 @@ class ArtistIndexTable extends Component {
|
||||||
style={style}
|
style={style}
|
||||||
columns={columns}
|
columns={columns}
|
||||||
artistId={artist.id}
|
artistId={artist.id}
|
||||||
languageProfileId={artist.languageProfileId}
|
|
||||||
qualityProfileId={artist.qualityProfileId}
|
qualityProfileId={artist.qualityProfileId}
|
||||||
metadataProfileId={artist.metadataProfileId}
|
metadataProfileId={artist.metadataProfileId}
|
||||||
showBanners={showBanners}
|
showBanners={showBanners}
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
const growableColumns = [
|
const growableColumns = [
|
||||||
'qualityProfileId',
|
'qualityProfileId',
|
||||||
'languageProfileId',
|
|
||||||
'path',
|
'path',
|
||||||
'tags'
|
'tags'
|
||||||
];
|
];
|
||||||
|
|
|
@ -19,7 +19,7 @@ function Legend(props) {
|
||||||
name="Cutoff Not Met"
|
name="Cutoff Not Met"
|
||||||
icon={icons.TRACK_FILE}
|
icon={icons.TRACK_FILE}
|
||||||
kind={kinds.WARNING}
|
kind={kinds.WARNING}
|
||||||
tooltip="Quality or language cutoff has not been met"
|
tooltip="Quality cutoff has not been met"
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,7 +7,6 @@ import BoolFilterBuilderRowValue from './BoolFilterBuilderRowValue';
|
||||||
import DateFilterBuilderRowValue from './DateFilterBuilderRowValue';
|
import DateFilterBuilderRowValue from './DateFilterBuilderRowValue';
|
||||||
import FilterBuilderRowValueConnector from './FilterBuilderRowValueConnector';
|
import FilterBuilderRowValueConnector from './FilterBuilderRowValueConnector';
|
||||||
import IndexerFilterBuilderRowValueConnector from './IndexerFilterBuilderRowValueConnector';
|
import IndexerFilterBuilderRowValueConnector from './IndexerFilterBuilderRowValueConnector';
|
||||||
import LanguageProfileFilterBuilderRowValueConnector from './LanguageProfileFilterBuilderRowValueConnector';
|
|
||||||
import MetadataProfileFilterBuilderRowValueConnector from './MetadataProfileFilterBuilderRowValueConnector';
|
import MetadataProfileFilterBuilderRowValueConnector from './MetadataProfileFilterBuilderRowValueConnector';
|
||||||
import ProtocolFilterBuilderRowValue from './ProtocolFilterBuilderRowValue';
|
import ProtocolFilterBuilderRowValue from './ProtocolFilterBuilderRowValue';
|
||||||
import QualityFilterBuilderRowValueConnector from './QualityFilterBuilderRowValueConnector';
|
import QualityFilterBuilderRowValueConnector from './QualityFilterBuilderRowValueConnector';
|
||||||
|
@ -61,9 +60,6 @@ function getRowValueConnector(selectedFilterBuilderProp) {
|
||||||
case filterBuilderValueTypes.INDEXER:
|
case filterBuilderValueTypes.INDEXER:
|
||||||
return IndexerFilterBuilderRowValueConnector;
|
return IndexerFilterBuilderRowValueConnector;
|
||||||
|
|
||||||
case filterBuilderValueTypes.LANGUAGE_PROFILE:
|
|
||||||
return LanguageProfileFilterBuilderRowValueConnector;
|
|
||||||
|
|
||||||
case filterBuilderValueTypes.METADATA_PROFILE:
|
case filterBuilderValueTypes.METADATA_PROFILE:
|
||||||
return MetadataProfileFilterBuilderRowValueConnector;
|
return MetadataProfileFilterBuilderRowValueConnector;
|
||||||
|
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import FilterBuilderRowValue from './FilterBuilderRowValue';
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(languageProfiles) => {
|
|
||||||
const tagList = languageProfiles.items.map((languageProfile) => {
|
|
||||||
const {
|
|
||||||
id,
|
|
||||||
name
|
|
||||||
} = languageProfile;
|
|
||||||
|
|
||||||
return {
|
|
||||||
id,
|
|
||||||
name
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
return {
|
|
||||||
tagList
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps)(FilterBuilderRowValue);
|
|
|
@ -14,7 +14,6 @@ import OAuthInputConnector from './OAuthInputConnector';
|
||||||
import PasswordInput from './PasswordInput';
|
import PasswordInput from './PasswordInput';
|
||||||
import PathInputConnector from './PathInputConnector';
|
import PathInputConnector from './PathInputConnector';
|
||||||
import QualityProfileSelectInputConnector from './QualityProfileSelectInputConnector';
|
import QualityProfileSelectInputConnector from './QualityProfileSelectInputConnector';
|
||||||
import LanguageProfileSelectInputConnector from './LanguageProfileSelectInputConnector';
|
|
||||||
import MetadataProfileSelectInputConnector from './MetadataProfileSelectInputConnector';
|
import MetadataProfileSelectInputConnector from './MetadataProfileSelectInputConnector';
|
||||||
import AlbumReleaseSelectInputConnector from './AlbumReleaseSelectInputConnector';
|
import AlbumReleaseSelectInputConnector from './AlbumReleaseSelectInputConnector';
|
||||||
import RootFolderSelectInputConnector from './RootFolderSelectInputConnector';
|
import RootFolderSelectInputConnector from './RootFolderSelectInputConnector';
|
||||||
|
@ -64,9 +63,6 @@ function getComponent(type) {
|
||||||
case inputTypes.QUALITY_PROFILE_SELECT:
|
case inputTypes.QUALITY_PROFILE_SELECT:
|
||||||
return QualityProfileSelectInputConnector;
|
return QualityProfileSelectInputConnector;
|
||||||
|
|
||||||
case inputTypes.LANGUAGE_PROFILE_SELECT:
|
|
||||||
return LanguageProfileSelectInputConnector;
|
|
||||||
|
|
||||||
case inputTypes.METADATA_PROFILE_SELECT:
|
case inputTypes.METADATA_PROFILE_SELECT:
|
||||||
return MetadataProfileSelectInputConnector;
|
return MetadataProfileSelectInputConnector;
|
||||||
|
|
||||||
|
|
|
@ -1,98 +0,0 @@
|
||||||
import _ from 'lodash';
|
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import sortByName from 'Utilities/Array/sortByName';
|
|
||||||
import SelectInput from './SelectInput';
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state, { includeNoChange }) => includeNoChange,
|
|
||||||
(state, { includeMixed }) => includeMixed,
|
|
||||||
(languageProfiles, includeNoChange, includeMixed) => {
|
|
||||||
const values = _.map(languageProfiles.items.sort(sortByName), (languageProfile) => {
|
|
||||||
return {
|
|
||||||
key: languageProfile.id,
|
|
||||||
value: languageProfile.name
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
if (includeNoChange) {
|
|
||||||
values.unshift({
|
|
||||||
key: 'noChange',
|
|
||||||
value: 'No Change',
|
|
||||||
disabled: true
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (includeMixed) {
|
|
||||||
values.unshift({
|
|
||||||
key: 'mixed',
|
|
||||||
value: '(Mixed)',
|
|
||||||
disabled: true
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
|
||||||
values
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
class LanguageProfileSelectInputConnector extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
componentDidMount() {
|
|
||||||
const {
|
|
||||||
name,
|
|
||||||
value,
|
|
||||||
values
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
if (!value || !_.some(values, (option) => parseInt(option.key) === value)) {
|
|
||||||
const firstValue = _.find(values, (option) => !isNaN(parseInt(option.key)));
|
|
||||||
|
|
||||||
if (firstValue) {
|
|
||||||
this.onChange({ name, value: firstValue.key });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onChange = ({ name, value }) => {
|
|
||||||
this.props.onChange({ name, value: parseInt(value) });
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
return (
|
|
||||||
<SelectInput
|
|
||||||
{...this.props}
|
|
||||||
onChange={this.onChange}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileSelectInputConnector.propTypes = {
|
|
||||||
name: PropTypes.string.isRequired,
|
|
||||||
value: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
|
|
||||||
values: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
includeNoChange: PropTypes.bool.isRequired,
|
|
||||||
onChange: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
LanguageProfileSelectInputConnector.defaultProps = {
|
|
||||||
includeNoChange: false
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps)(LanguageProfileSelectInputConnector);
|
|
|
@ -11,7 +11,6 @@ function ErrorPage(props) {
|
||||||
customFiltersError,
|
customFiltersError,
|
||||||
tagsError,
|
tagsError,
|
||||||
qualityProfilesError,
|
qualityProfilesError,
|
||||||
languageProfilesError,
|
|
||||||
metadataProfilesError,
|
metadataProfilesError,
|
||||||
uiSettingsError,
|
uiSettingsError,
|
||||||
systemStatusError
|
systemStatusError
|
||||||
|
@ -29,8 +28,6 @@ function ErrorPage(props) {
|
||||||
errorMessage = getErrorMessage(tagsError, 'Failed to load tags from API');
|
errorMessage = getErrorMessage(tagsError, 'Failed to load tags from API');
|
||||||
} else if (qualityProfilesError) {
|
} else if (qualityProfilesError) {
|
||||||
errorMessage = getErrorMessage(qualityProfilesError, 'Failed to load quality profiles from API');
|
errorMessage = getErrorMessage(qualityProfilesError, 'Failed to load quality profiles from API');
|
||||||
} else if (languageProfilesError) {
|
|
||||||
errorMessage = getErrorMessage(languageProfilesError, 'Failed to load language profiles from API');
|
|
||||||
} else if (metadataProfilesError) {
|
} else if (metadataProfilesError) {
|
||||||
errorMessage = getErrorMessage(metadataProfilesError, 'Failed to load metadata profiles from API');
|
errorMessage = getErrorMessage(metadataProfilesError, 'Failed to load metadata profiles from API');
|
||||||
} else if (uiSettingsError) {
|
} else if (uiSettingsError) {
|
||||||
|
@ -59,7 +56,6 @@ ErrorPage.propTypes = {
|
||||||
customFiltersError: PropTypes.object,
|
customFiltersError: PropTypes.object,
|
||||||
tagsError: PropTypes.object,
|
tagsError: PropTypes.object,
|
||||||
qualityProfilesError: PropTypes.object,
|
qualityProfilesError: PropTypes.object,
|
||||||
languageProfilesError: PropTypes.object,
|
|
||||||
metadataProfilesError: PropTypes.object,
|
metadataProfilesError: PropTypes.object,
|
||||||
uiSettingsError: PropTypes.object,
|
uiSettingsError: PropTypes.object,
|
||||||
systemStatusError: PropTypes.object
|
systemStatusError: PropTypes.object
|
||||||
|
|
|
@ -8,7 +8,7 @@ import { saveDimensions, setIsSidebarVisible } from 'Store/Actions/appActions';
|
||||||
import { fetchCustomFilters } from 'Store/Actions/customFilterActions';
|
import { fetchCustomFilters } from 'Store/Actions/customFilterActions';
|
||||||
import { fetchArtist } from 'Store/Actions/artistActions';
|
import { fetchArtist } from 'Store/Actions/artistActions';
|
||||||
import { fetchTags } from 'Store/Actions/tagActions';
|
import { fetchTags } from 'Store/Actions/tagActions';
|
||||||
import { fetchQualityProfiles, fetchLanguageProfiles, fetchMetadataProfiles, fetchUISettings, fetchImportLists } from 'Store/Actions/settingsActions';
|
import { fetchQualityProfiles, fetchMetadataProfiles, fetchUISettings, fetchImportLists } from 'Store/Actions/settingsActions';
|
||||||
import { fetchStatus } from 'Store/Actions/systemActions';
|
import { fetchStatus } from 'Store/Actions/systemActions';
|
||||||
import ErrorPage from './ErrorPage';
|
import ErrorPage from './ErrorPage';
|
||||||
import LoadingPage from './LoadingPage';
|
import LoadingPage from './LoadingPage';
|
||||||
|
@ -48,7 +48,6 @@ const selectIsPopulated = createSelector(
|
||||||
(state) => state.tags.isPopulated,
|
(state) => state.tags.isPopulated,
|
||||||
(state) => state.settings.ui.isPopulated,
|
(state) => state.settings.ui.isPopulated,
|
||||||
(state) => state.settings.qualityProfiles.isPopulated,
|
(state) => state.settings.qualityProfiles.isPopulated,
|
||||||
(state) => state.settings.languageProfiles.isPopulated,
|
|
||||||
(state) => state.settings.metadataProfiles.isPopulated,
|
(state) => state.settings.metadataProfiles.isPopulated,
|
||||||
(state) => state.settings.importLists.isPopulated,
|
(state) => state.settings.importLists.isPopulated,
|
||||||
(state) => state.system.status.isPopulated,
|
(state) => state.system.status.isPopulated,
|
||||||
|
@ -58,7 +57,6 @@ const selectIsPopulated = createSelector(
|
||||||
tagsIsPopulated,
|
tagsIsPopulated,
|
||||||
uiSettingsIsPopulated,
|
uiSettingsIsPopulated,
|
||||||
qualityProfilesIsPopulated,
|
qualityProfilesIsPopulated,
|
||||||
languageProfilesIsPopulated,
|
|
||||||
metadataProfilesIsPopulated,
|
metadataProfilesIsPopulated,
|
||||||
importListsIsPopulated,
|
importListsIsPopulated,
|
||||||
systemStatusIsPopulated
|
systemStatusIsPopulated
|
||||||
|
@ -69,7 +67,6 @@ const selectIsPopulated = createSelector(
|
||||||
tagsIsPopulated &&
|
tagsIsPopulated &&
|
||||||
uiSettingsIsPopulated &&
|
uiSettingsIsPopulated &&
|
||||||
qualityProfilesIsPopulated &&
|
qualityProfilesIsPopulated &&
|
||||||
languageProfilesIsPopulated &&
|
|
||||||
metadataProfilesIsPopulated &&
|
metadataProfilesIsPopulated &&
|
||||||
importListsIsPopulated &&
|
importListsIsPopulated &&
|
||||||
systemStatusIsPopulated
|
systemStatusIsPopulated
|
||||||
|
@ -83,7 +80,6 @@ const selectErrors = createSelector(
|
||||||
(state) => state.tags.error,
|
(state) => state.tags.error,
|
||||||
(state) => state.settings.ui.error,
|
(state) => state.settings.ui.error,
|
||||||
(state) => state.settings.qualityProfiles.error,
|
(state) => state.settings.qualityProfiles.error,
|
||||||
(state) => state.settings.languageProfiles.error,
|
|
||||||
(state) => state.settings.metadataProfiles.error,
|
(state) => state.settings.metadataProfiles.error,
|
||||||
(state) => state.settings.importLists.error,
|
(state) => state.settings.importLists.error,
|
||||||
(state) => state.system.status.error,
|
(state) => state.system.status.error,
|
||||||
|
@ -93,7 +89,6 @@ const selectErrors = createSelector(
|
||||||
tagsError,
|
tagsError,
|
||||||
uiSettingsError,
|
uiSettingsError,
|
||||||
qualityProfilesError,
|
qualityProfilesError,
|
||||||
languageProfilesError,
|
|
||||||
metadataProfilesError,
|
metadataProfilesError,
|
||||||
importListsError,
|
importListsError,
|
||||||
systemStatusError
|
systemStatusError
|
||||||
|
@ -104,7 +99,6 @@ const selectErrors = createSelector(
|
||||||
tagsError ||
|
tagsError ||
|
||||||
uiSettingsError ||
|
uiSettingsError ||
|
||||||
qualityProfilesError ||
|
qualityProfilesError ||
|
||||||
languageProfilesError ||
|
|
||||||
metadataProfilesError ||
|
metadataProfilesError ||
|
||||||
importListsError ||
|
importListsError ||
|
||||||
systemStatusError
|
systemStatusError
|
||||||
|
@ -117,7 +111,6 @@ const selectErrors = createSelector(
|
||||||
tagsError,
|
tagsError,
|
||||||
uiSettingsError,
|
uiSettingsError,
|
||||||
qualityProfilesError,
|
qualityProfilesError,
|
||||||
languageProfilesError,
|
|
||||||
metadataProfilesError,
|
metadataProfilesError,
|
||||||
importListsError,
|
importListsError,
|
||||||
systemStatusError
|
systemStatusError
|
||||||
|
@ -164,9 +157,6 @@ function createMapDispatchToProps(dispatch, props) {
|
||||||
dispatchFetchQualityProfiles() {
|
dispatchFetchQualityProfiles() {
|
||||||
dispatch(fetchQualityProfiles());
|
dispatch(fetchQualityProfiles());
|
||||||
},
|
},
|
||||||
dispatchFetchLanguageProfiles() {
|
|
||||||
dispatch(fetchLanguageProfiles());
|
|
||||||
},
|
|
||||||
dispatchFetchMetadataProfiles() {
|
dispatchFetchMetadataProfiles() {
|
||||||
dispatch(fetchMetadataProfiles());
|
dispatch(fetchMetadataProfiles());
|
||||||
},
|
},
|
||||||
|
@ -207,7 +197,6 @@ class PageConnector extends Component {
|
||||||
this.props.dispatchFetchCustomFilters();
|
this.props.dispatchFetchCustomFilters();
|
||||||
this.props.dispatchFetchTags();
|
this.props.dispatchFetchTags();
|
||||||
this.props.dispatchFetchQualityProfiles();
|
this.props.dispatchFetchQualityProfiles();
|
||||||
this.props.dispatchFetchLanguageProfiles();
|
|
||||||
this.props.dispatchFetchMetadataProfiles();
|
this.props.dispatchFetchMetadataProfiles();
|
||||||
this.props.dispatchFetchImportLists();
|
this.props.dispatchFetchImportLists();
|
||||||
this.props.dispatchFetchUISettings();
|
this.props.dispatchFetchUISettings();
|
||||||
|
@ -232,7 +221,6 @@ class PageConnector extends Component {
|
||||||
dispatchFetchArtist,
|
dispatchFetchArtist,
|
||||||
dispatchFetchTags,
|
dispatchFetchTags,
|
||||||
dispatchFetchQualityProfiles,
|
dispatchFetchQualityProfiles,
|
||||||
dispatchFetchLanguageProfiles,
|
|
||||||
dispatchFetchMetadataProfiles,
|
dispatchFetchMetadataProfiles,
|
||||||
dispatchFetchImportLists,
|
dispatchFetchImportLists,
|
||||||
dispatchFetchUISettings,
|
dispatchFetchUISettings,
|
||||||
|
@ -272,7 +260,6 @@ PageConnector.propTypes = {
|
||||||
dispatchFetchCustomFilters: PropTypes.func.isRequired,
|
dispatchFetchCustomFilters: PropTypes.func.isRequired,
|
||||||
dispatchFetchTags: PropTypes.func.isRequired,
|
dispatchFetchTags: PropTypes.func.isRequired,
|
||||||
dispatchFetchQualityProfiles: PropTypes.func.isRequired,
|
dispatchFetchQualityProfiles: PropTypes.func.isRequired,
|
||||||
dispatchFetchLanguageProfiles: PropTypes.func.isRequired,
|
|
||||||
dispatchFetchMetadataProfiles: PropTypes.func.isRequired,
|
dispatchFetchMetadataProfiles: PropTypes.func.isRequired,
|
||||||
dispatchFetchImportLists: PropTypes.func.isRequired,
|
dispatchFetchImportLists: PropTypes.func.isRequired,
|
||||||
dispatchFetchUISettings: PropTypes.func.isRequired,
|
dispatchFetchUISettings: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -3,7 +3,6 @@ export const BYTES = 'bytes';
|
||||||
export const DATE = 'date';
|
export const DATE = 'date';
|
||||||
export const DEFAULT = 'default';
|
export const DEFAULT = 'default';
|
||||||
export const INDEXER = 'indexer';
|
export const INDEXER = 'indexer';
|
||||||
export const LANGUAGE_PROFILE = 'languageProfile';
|
|
||||||
export const METADATA_PROFILE = 'metadataProfile';
|
export const METADATA_PROFILE = 'metadataProfile';
|
||||||
export const PROTOCOL = 'protocol';
|
export const PROTOCOL = 'protocol';
|
||||||
export const QUALITY = 'quality';
|
export const QUALITY = 'quality';
|
||||||
|
|
|
@ -10,7 +10,6 @@ export const OAUTH = 'oauth';
|
||||||
export const PASSWORD = 'password';
|
export const PASSWORD = 'password';
|
||||||
export const PATH = 'path';
|
export const PATH = 'path';
|
||||||
export const QUALITY_PROFILE_SELECT = 'qualityProfileSelect';
|
export const QUALITY_PROFILE_SELECT = 'qualityProfileSelect';
|
||||||
export const LANGUAGE_PROFILE_SELECT = 'languageProfileSelect';
|
|
||||||
export const METADATA_PROFILE_SELECT = 'metadataProfileSelect';
|
export const METADATA_PROFILE_SELECT = 'metadataProfileSelect';
|
||||||
export const ALBUM_RELEASE_SELECT = 'albumReleaseSelect';
|
export const ALBUM_RELEASE_SELECT = 'albumReleaseSelect';
|
||||||
export const ROOT_FOLDER_SELECT = 'rootFolderSelect';
|
export const ROOT_FOLDER_SELECT = 'rootFolderSelect';
|
||||||
|
@ -33,7 +32,6 @@ export const all = [
|
||||||
PASSWORD,
|
PASSWORD,
|
||||||
PATH,
|
PATH,
|
||||||
QUALITY_PROFILE_SELECT,
|
QUALITY_PROFILE_SELECT,
|
||||||
LANGUAGE_PROFILE_SELECT,
|
|
||||||
METADATA_PROFILE_SELECT,
|
METADATA_PROFILE_SELECT,
|
||||||
ALBUM_RELEASE_SELECT,
|
ALBUM_RELEASE_SELECT,
|
||||||
ROOT_FOLDER_SELECT,
|
ROOT_FOLDER_SELECT,
|
||||||
|
|
|
@ -56,12 +56,6 @@ const columns = [
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isSortable: true,
|
|
||||||
isVisible: true
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'size',
|
name: 'size',
|
||||||
label: 'Size',
|
label: 'Size',
|
||||||
|
|
|
@ -127,7 +127,6 @@ class InteractiveImportModalContentConnector extends Component {
|
||||||
albumReleaseId,
|
albumReleaseId,
|
||||||
tracks,
|
tracks,
|
||||||
quality,
|
quality,
|
||||||
language,
|
|
||||||
disableReleaseSwitching
|
disableReleaseSwitching
|
||||||
} = item;
|
} = item;
|
||||||
|
|
||||||
|
@ -151,11 +150,6 @@ class InteractiveImportModalContentConnector extends Component {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!language) {
|
|
||||||
this.setState({ interactiveImportErrorMessage: 'Language must be chosen for each selected file' });
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
files.push({
|
files.push({
|
||||||
path: item.path,
|
path: item.path,
|
||||||
folderName: item.folderName,
|
folderName: item.folderName,
|
||||||
|
@ -164,7 +158,6 @@ class InteractiveImportModalContentConnector extends Component {
|
||||||
albumReleaseId,
|
albumReleaseId,
|
||||||
trackIds: _.map(tracks, 'id'),
|
trackIds: _.map(tracks, 'id'),
|
||||||
quality,
|
quality,
|
||||||
language,
|
|
||||||
downloadId: this.props.downloadId,
|
downloadId: this.props.downloadId,
|
||||||
disableReleaseSwitching
|
disableReleaseSwitching
|
||||||
});
|
});
|
||||||
|
|
|
@ -4,8 +4,7 @@
|
||||||
word-break: break-all;
|
word-break: break-all;
|
||||||
}
|
}
|
||||||
|
|
||||||
.quality,
|
.quality {
|
||||||
.language {
|
|
||||||
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
||||||
|
|
||||||
text-align: center;
|
text-align: center;
|
||||||
|
|
|
@ -11,12 +11,10 @@ import TableSelectCell from 'Components/Table/Cells/TableSelectCell';
|
||||||
import Popover from 'Components/Tooltip/Popover';
|
import Popover from 'Components/Tooltip/Popover';
|
||||||
import Tooltip from 'Components/Tooltip/Tooltip';
|
import Tooltip from 'Components/Tooltip/Tooltip';
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import SelectArtistModal from 'InteractiveImport/Artist/SelectArtistModal';
|
import SelectArtistModal from 'InteractiveImport/Artist/SelectArtistModal';
|
||||||
import SelectAlbumModal from 'InteractiveImport/Album/SelectAlbumModal';
|
import SelectAlbumModal from 'InteractiveImport/Album/SelectAlbumModal';
|
||||||
import SelectTrackModal from 'InteractiveImport/Track/SelectTrackModal';
|
import SelectTrackModal from 'InteractiveImport/Track/SelectTrackModal';
|
||||||
import SelectQualityModal from 'InteractiveImport/Quality/SelectQualityModal';
|
import SelectQualityModal from 'InteractiveImport/Quality/SelectQualityModal';
|
||||||
import SelectLanguageModal from 'InteractiveImport/Language/SelectLanguageModal';
|
|
||||||
import InteractiveImportRowCellPlaceholder from './InteractiveImportRowCellPlaceholder';
|
import InteractiveImportRowCellPlaceholder from './InteractiveImportRowCellPlaceholder';
|
||||||
import LoadingIndicator from 'Components/Loading/LoadingIndicator';
|
import LoadingIndicator from 'Components/Loading/LoadingIndicator';
|
||||||
import styles from './InteractiveImportRow.css';
|
import styles from './InteractiveImportRow.css';
|
||||||
|
@ -33,8 +31,7 @@ class InteractiveImportRow extends Component {
|
||||||
isSelectArtistModalOpen: false,
|
isSelectArtistModalOpen: false,
|
||||||
isSelectAlbumModalOpen: false,
|
isSelectAlbumModalOpen: false,
|
||||||
isSelectTrackModalOpen: false,
|
isSelectTrackModalOpen: false,
|
||||||
isSelectQualityModalOpen: false,
|
isSelectQualityModalOpen: false
|
||||||
isSelectLanguageModalOpen: false
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -44,16 +41,14 @@ class InteractiveImportRow extends Component {
|
||||||
artist,
|
artist,
|
||||||
album,
|
album,
|
||||||
tracks,
|
tracks,
|
||||||
quality,
|
quality
|
||||||
language
|
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
|
||||||
if (
|
if (
|
||||||
artist &&
|
artist &&
|
||||||
album != null &&
|
album != null &&
|
||||||
tracks.length &&
|
tracks.length &&
|
||||||
quality &&
|
quality
|
||||||
language
|
|
||||||
) {
|
) {
|
||||||
this.props.onSelectedChange({ id, value: true });
|
this.props.onSelectedChange({ id, value: true });
|
||||||
}
|
}
|
||||||
|
@ -66,7 +61,6 @@ class InteractiveImportRow extends Component {
|
||||||
album,
|
album,
|
||||||
tracks,
|
tracks,
|
||||||
quality,
|
quality,
|
||||||
language,
|
|
||||||
isSelected,
|
isSelected,
|
||||||
onValidRowChange
|
onValidRowChange
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
@ -76,7 +70,6 @@ class InteractiveImportRow extends Component {
|
||||||
prevProps.album === album &&
|
prevProps.album === album &&
|
||||||
!hasDifferentItems(prevProps.tracks, tracks) &&
|
!hasDifferentItems(prevProps.tracks, tracks) &&
|
||||||
prevProps.quality === quality &&
|
prevProps.quality === quality &&
|
||||||
prevProps.language === language &&
|
|
||||||
prevProps.isSelected === isSelected
|
prevProps.isSelected === isSelected
|
||||||
) {
|
) {
|
||||||
return;
|
return;
|
||||||
|
@ -86,8 +79,7 @@ class InteractiveImportRow extends Component {
|
||||||
artist &&
|
artist &&
|
||||||
album &&
|
album &&
|
||||||
tracks.length &&
|
tracks.length &&
|
||||||
quality &&
|
quality
|
||||||
language
|
|
||||||
);
|
);
|
||||||
|
|
||||||
if (isSelected && !isValid) {
|
if (isSelected && !isValid) {
|
||||||
|
@ -130,10 +122,6 @@ class InteractiveImportRow extends Component {
|
||||||
this.setState({ isSelectQualityModalOpen: true });
|
this.setState({ isSelectQualityModalOpen: true });
|
||||||
}
|
}
|
||||||
|
|
||||||
onSelectLanguagePress = () => {
|
|
||||||
this.setState({ isSelectLanguageModalOpen: true });
|
|
||||||
}
|
|
||||||
|
|
||||||
onSelectArtistModalClose = (changed) => {
|
onSelectArtistModalClose = (changed) => {
|
||||||
this.setState({ isSelectArtistModalOpen: false });
|
this.setState({ isSelectArtistModalOpen: false });
|
||||||
this.selectRowAfterChange(changed);
|
this.selectRowAfterChange(changed);
|
||||||
|
@ -154,11 +142,6 @@ class InteractiveImportRow extends Component {
|
||||||
this.selectRowAfterChange(changed);
|
this.selectRowAfterChange(changed);
|
||||||
}
|
}
|
||||||
|
|
||||||
onSelectLanguageModalClose = (changed) => {
|
|
||||||
this.setState({ isSelectLanguageModalOpen: false });
|
|
||||||
this.selectRowAfterChange(changed);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// Render
|
// Render
|
||||||
|
|
||||||
|
@ -172,7 +155,6 @@ class InteractiveImportRow extends Component {
|
||||||
albumReleaseId,
|
albumReleaseId,
|
||||||
tracks,
|
tracks,
|
||||||
quality,
|
quality,
|
||||||
language,
|
|
||||||
size,
|
size,
|
||||||
rejections,
|
rejections,
|
||||||
audioTags,
|
audioTags,
|
||||||
|
@ -186,8 +168,7 @@ class InteractiveImportRow extends Component {
|
||||||
isSelectArtistModalOpen,
|
isSelectArtistModalOpen,
|
||||||
isSelectAlbumModalOpen,
|
isSelectAlbumModalOpen,
|
||||||
isSelectTrackModalOpen,
|
isSelectTrackModalOpen,
|
||||||
isSelectQualityModalOpen,
|
isSelectQualityModalOpen
|
||||||
isSelectLanguageModalOpen
|
|
||||||
} = this.state;
|
} = this.state;
|
||||||
|
|
||||||
const artistName = artist ? artist.artistName : '';
|
const artistName = artist ? artist.artistName : '';
|
||||||
|
@ -203,7 +184,6 @@ class InteractiveImportRow extends Component {
|
||||||
const showTrackNumbersPlaceholder = !isSaving && isSelected && !!album && !tracks.length;
|
const showTrackNumbersPlaceholder = !isSaving && isSelected && !!album && !tracks.length;
|
||||||
const showTrackNumbersLoading = isSaving && !tracks.length;
|
const showTrackNumbersLoading = isSaving && !tracks.length;
|
||||||
const showQualityPlaceholder = isSelected && !quality;
|
const showQualityPlaceholder = isSelected && !quality;
|
||||||
const showLanguagePlaceholder = isSelected && !language;
|
|
||||||
|
|
||||||
const pathCellContents = (
|
const pathCellContents = (
|
||||||
<div>
|
<div>
|
||||||
|
@ -288,25 +268,6 @@ class InteractiveImportRow extends Component {
|
||||||
}
|
}
|
||||||
</TableRowCellButton>
|
</TableRowCellButton>
|
||||||
|
|
||||||
<TableRowCellButton
|
|
||||||
className={styles.language}
|
|
||||||
title="Click to change language"
|
|
||||||
onPress={this.onSelectLanguagePress}
|
|
||||||
>
|
|
||||||
{
|
|
||||||
showLanguagePlaceholder &&
|
|
||||||
<InteractiveImportRowCellPlaceholder />
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
!showLanguagePlaceholder && !!language &&
|
|
||||||
<TrackLanguage
|
|
||||||
className={styles.label}
|
|
||||||
language={language}
|
|
||||||
/>
|
|
||||||
}
|
|
||||||
</TableRowCellButton>
|
|
||||||
|
|
||||||
<TableRowCell>
|
<TableRowCell>
|
||||||
{formatBytes(size)}
|
{formatBytes(size)}
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
@ -376,13 +337,6 @@ class InteractiveImportRow extends Component {
|
||||||
real={quality ? quality.revision.real > 0 : false}
|
real={quality ? quality.revision.real > 0 : false}
|
||||||
onModalClose={this.onSelectQualityModalClose}
|
onModalClose={this.onSelectQualityModalClose}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
<SelectLanguageModal
|
|
||||||
isOpen={isSelectLanguageModalOpen}
|
|
||||||
id={id}
|
|
||||||
languageId={language ? language.id : 0}
|
|
||||||
onModalClose={this.onSelectLanguageModalClose}
|
|
||||||
/>
|
|
||||||
</TableRow>
|
</TableRow>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -398,7 +352,6 @@ InteractiveImportRow.propTypes = {
|
||||||
albumReleaseId: PropTypes.number,
|
albumReleaseId: PropTypes.number,
|
||||||
tracks: PropTypes.arrayOf(PropTypes.object).isRequired,
|
tracks: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
quality: PropTypes.object,
|
quality: PropTypes.object,
|
||||||
language: PropTypes.object,
|
|
||||||
size: PropTypes.number.isRequired,
|
size: PropTypes.number.isRequired,
|
||||||
rejections: PropTypes.arrayOf(PropTypes.object).isRequired,
|
rejections: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
audioTags: PropTypes.object.isRequired,
|
audioTags: PropTypes.object.isRequired,
|
||||||
|
|
|
@ -1,37 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import Modal from 'Components/Modal/Modal';
|
|
||||||
import SelectLanguageModalContentConnector from './SelectLanguageModalContentConnector';
|
|
||||||
|
|
||||||
class SelectLanguageModal extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
isOpen,
|
|
||||||
onModalClose,
|
|
||||||
...otherProps
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Modal
|
|
||||||
isOpen={isOpen}
|
|
||||||
onModalClose={onModalClose}
|
|
||||||
>
|
|
||||||
<SelectLanguageModalContentConnector
|
|
||||||
{...otherProps}
|
|
||||||
onModalClose={onModalClose}
|
|
||||||
/>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
SelectLanguageModal.propTypes = {
|
|
||||||
isOpen: PropTypes.bool.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default SelectLanguageModal;
|
|
|
@ -1,87 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React from 'react';
|
|
||||||
import { inputTypes } from 'Helpers/Props';
|
|
||||||
import Button from 'Components/Link/Button';
|
|
||||||
import LoadingIndicator from 'Components/Loading/LoadingIndicator';
|
|
||||||
import Form from 'Components/Form/Form';
|
|
||||||
import FormGroup from 'Components/Form/FormGroup';
|
|
||||||
import FormLabel from 'Components/Form/FormLabel';
|
|
||||||
import FormInputGroup from 'Components/Form/FormInputGroup';
|
|
||||||
import ModalContent from 'Components/Modal/ModalContent';
|
|
||||||
import ModalHeader from 'Components/Modal/ModalHeader';
|
|
||||||
import ModalBody from 'Components/Modal/ModalBody';
|
|
||||||
import ModalFooter from 'Components/Modal/ModalFooter';
|
|
||||||
|
|
||||||
function SelectLanguageModalContent(props) {
|
|
||||||
const {
|
|
||||||
languageId,
|
|
||||||
isFetching,
|
|
||||||
isPopulated,
|
|
||||||
error,
|
|
||||||
items,
|
|
||||||
onModalClose,
|
|
||||||
onLanguageSelect
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
const languageOptions = items.map(({ language }) => {
|
|
||||||
return {
|
|
||||||
key: language.id,
|
|
||||||
value: language.name
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
return (
|
|
||||||
<ModalContent onModalClose={onModalClose}>
|
|
||||||
<ModalHeader>
|
|
||||||
Manual Import - Select Language
|
|
||||||
</ModalHeader>
|
|
||||||
|
|
||||||
<ModalBody>
|
|
||||||
{
|
|
||||||
isFetching &&
|
|
||||||
<LoadingIndicator />
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
!isFetching && !!error &&
|
|
||||||
<div>Unable to load languages</div>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
isPopulated && !error &&
|
|
||||||
<Form>
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>Language</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.SELECT}
|
|
||||||
name="language"
|
|
||||||
value={languageId}
|
|
||||||
values={languageOptions}
|
|
||||||
onChange={onLanguageSelect}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
</Form>
|
|
||||||
}
|
|
||||||
</ModalBody>
|
|
||||||
|
|
||||||
<ModalFooter>
|
|
||||||
<Button onPress={onModalClose}>
|
|
||||||
Cancel
|
|
||||||
</Button>
|
|
||||||
</ModalFooter>
|
|
||||||
</ModalContent>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
SelectLanguageModalContent.propTypes = {
|
|
||||||
languageId: PropTypes.number.isRequired,
|
|
||||||
isFetching: PropTypes.bool.isRequired,
|
|
||||||
isPopulated: PropTypes.bool.isRequired,
|
|
||||||
error: PropTypes.object,
|
|
||||||
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
onLanguageSelect: PropTypes.func.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default SelectLanguageModalContent;
|
|
|
@ -1,87 +0,0 @@
|
||||||
import _ from 'lodash';
|
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import { fetchLanguageProfileSchema } from 'Store/Actions/settingsActions';
|
|
||||||
import { updateInteractiveImportItem } from 'Store/Actions/interactiveImportActions';
|
|
||||||
import SelectLanguageModalContent from './SelectLanguageModalContent';
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(languageProfiles) => {
|
|
||||||
const {
|
|
||||||
isSchemaFetching: isFetching,
|
|
||||||
isSchemaPopulated: isPopulated,
|
|
||||||
schemaError: error,
|
|
||||||
schema
|
|
||||||
} = languageProfiles;
|
|
||||||
|
|
||||||
return {
|
|
||||||
isFetching,
|
|
||||||
isPopulated,
|
|
||||||
error,
|
|
||||||
items: schema.languages ? [...schema.languages].reverse() : []
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
const mapDispatchToProps = {
|
|
||||||
fetchLanguageProfileSchema,
|
|
||||||
updateInteractiveImportItem
|
|
||||||
};
|
|
||||||
|
|
||||||
class SelectLanguageModalContentConnector extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
componentDidMount = () => {
|
|
||||||
if (!this.props.isPopulated) {
|
|
||||||
this.props.fetchLanguageProfileSchema();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onLanguageSelect = ({ value }) => {
|
|
||||||
const languageId = parseInt(value);
|
|
||||||
const language = _.find(this.props.items,
|
|
||||||
(item) => item.language.id === languageId).language;
|
|
||||||
|
|
||||||
this.props.updateInteractiveImportItem({
|
|
||||||
id: this.props.id,
|
|
||||||
language
|
|
||||||
});
|
|
||||||
|
|
||||||
this.props.onModalClose(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
return (
|
|
||||||
<SelectLanguageModalContent
|
|
||||||
{...this.props}
|
|
||||||
onLanguageSelect={this.onLanguageSelect}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
SelectLanguageModalContentConnector.propTypes = {
|
|
||||||
id: PropTypes.number.isRequired,
|
|
||||||
isFetching: PropTypes.bool.isRequired,
|
|
||||||
isPopulated: PropTypes.bool.isRequired,
|
|
||||||
error: PropTypes.object,
|
|
||||||
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
fetchLanguageProfileSchema: PropTypes.func.isRequired,
|
|
||||||
updateInteractiveImportItem: PropTypes.func.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps, mapDispatchToProps)(SelectLanguageModalContentConnector);
|
|
|
@ -48,12 +48,6 @@ const columns = [
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageWeight',
|
|
||||||
label: 'Language',
|
|
||||||
isSortable: true,
|
|
||||||
isVisible: true
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'qualityWeight',
|
name: 'qualityWeight',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
|
|
@ -4,17 +4,12 @@
|
||||||
word-break: break-all;
|
word-break: break-all;
|
||||||
}
|
}
|
||||||
|
|
||||||
.quality,
|
.quality {
|
||||||
.language {
|
|
||||||
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
||||||
|
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.language {
|
|
||||||
width: 100px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.preferredWordScore {
|
.preferredWordScore {
|
||||||
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
composes: cell from '~Components/Table/Cells/TableRowCell.css';
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,6 @@ import ConfirmModal from 'Components/Modal/ConfirmModal';
|
||||||
import TableRow from 'Components/Table/TableRow';
|
import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import Popover from 'Components/Tooltip/Popover';
|
import Popover from 'Components/Tooltip/Popover';
|
||||||
import TrackLanguage from 'Album/TrackLanguage';
|
|
||||||
import TrackQuality from 'Album/TrackQuality';
|
import TrackQuality from 'Album/TrackQuality';
|
||||||
import ProtocolLabel from 'Activity/Queue/ProtocolLabel';
|
import ProtocolLabel from 'Activity/Queue/ProtocolLabel';
|
||||||
import Peers from './Peers';
|
import Peers from './Peers';
|
||||||
|
@ -112,7 +111,6 @@ class InteractiveSearchRow extends Component {
|
||||||
seeders,
|
seeders,
|
||||||
leechers,
|
leechers,
|
||||||
quality,
|
quality,
|
||||||
language,
|
|
||||||
preferredWordScore,
|
preferredWordScore,
|
||||||
rejections,
|
rejections,
|
||||||
downloadAllowed,
|
downloadAllowed,
|
||||||
|
@ -162,10 +160,6 @@ class InteractiveSearchRow extends Component {
|
||||||
}
|
}
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
|
||||||
<TableRowCell className={styles.language}>
|
|
||||||
<TrackLanguage language={language} />
|
|
||||||
</TableRowCell>
|
|
||||||
|
|
||||||
<TableRowCell className={styles.quality}>
|
<TableRowCell className={styles.quality}>
|
||||||
<TrackQuality quality={quality} />
|
<TrackQuality quality={quality} />
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
@ -245,7 +239,6 @@ InteractiveSearchRow.propTypes = {
|
||||||
seeders: PropTypes.number,
|
seeders: PropTypes.number,
|
||||||
leechers: PropTypes.number,
|
leechers: PropTypes.number,
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
preferredWordScore: PropTypes.number.isRequired,
|
preferredWordScore: PropTypes.number.isRequired,
|
||||||
rejections: PropTypes.arrayOf(PropTypes.string).isRequired,
|
rejections: PropTypes.arrayOf(PropTypes.string).isRequired,
|
||||||
downloadAllowed: PropTypes.bool.isRequired,
|
downloadAllowed: PropTypes.bool.isRequired,
|
||||||
|
|
|
@ -4,7 +4,6 @@
|
||||||
margin-right: auto;
|
margin-right: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
.hideLanguageProfile,
|
|
||||||
.hideMetadataProfile {
|
.hideMetadataProfile {
|
||||||
composes: group from '~Components/Form/FormGroup.css';
|
composes: group from '~Components/Form/FormGroup.css';
|
||||||
|
|
||||||
|
|
|
@ -62,7 +62,6 @@ function EditImportListModalContent(props) {
|
||||||
onSavePress,
|
onSavePress,
|
||||||
onTestPress,
|
onTestPress,
|
||||||
onDeleteImportListPress,
|
onDeleteImportListPress,
|
||||||
showLanguageProfile,
|
|
||||||
showMetadataProfile,
|
showMetadataProfile,
|
||||||
...otherProps
|
...otherProps
|
||||||
} = props;
|
} = props;
|
||||||
|
@ -74,7 +73,6 @@ function EditImportListModalContent(props) {
|
||||||
shouldMonitor,
|
shouldMonitor,
|
||||||
rootFolderPath,
|
rootFolderPath,
|
||||||
qualityProfileId,
|
qualityProfileId,
|
||||||
languageProfileId,
|
|
||||||
metadataProfileId,
|
metadataProfileId,
|
||||||
tags,
|
tags,
|
||||||
fields
|
fields
|
||||||
|
@ -174,18 +172,6 @@ function EditImportListModalContent(props) {
|
||||||
/>
|
/>
|
||||||
</FormGroup>
|
</FormGroup>
|
||||||
|
|
||||||
<FormGroup className={showLanguageProfile ? undefined : styles.hideLanguageProfile}>
|
|
||||||
<FormLabel>Language Profile</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.LANGUAGE_PROFILE_SELECT}
|
|
||||||
name="languageProfileId"
|
|
||||||
helpText={'Language Profile list items should be added with'}
|
|
||||||
{...languageProfileId}
|
|
||||||
onChange={onInputChange}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
|
|
||||||
<FormGroup className={showMetadataProfile ? undefined : styles.hideMetadataProfile}>
|
<FormGroup className={showMetadataProfile ? undefined : styles.hideMetadataProfile}>
|
||||||
<FormLabel>Metadata Profile</FormLabel>
|
<FormLabel>Metadata Profile</FormLabel>
|
||||||
|
|
||||||
|
@ -280,7 +266,6 @@ EditImportListModalContent.propTypes = {
|
||||||
isTesting: PropTypes.bool.isRequired,
|
isTesting: PropTypes.bool.isRequired,
|
||||||
saveError: PropTypes.object,
|
saveError: PropTypes.object,
|
||||||
item: PropTypes.object.isRequired,
|
item: PropTypes.object.isRequired,
|
||||||
showLanguageProfile: PropTypes.bool.isRequired,
|
|
||||||
showMetadataProfile: PropTypes.bool.isRequired,
|
showMetadataProfile: PropTypes.bool.isRequired,
|
||||||
onInputChange: PropTypes.func.isRequired,
|
onInputChange: PropTypes.func.isRequired,
|
||||||
onFieldChange: PropTypes.func.isRequired,
|
onFieldChange: PropTypes.func.isRequired,
|
||||||
|
|
|
@ -9,13 +9,11 @@ import EditImportListModalContent from './EditImportListModalContent';
|
||||||
function createMapStateToProps() {
|
function createMapStateToProps() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
(state) => state.settings.advancedSettings,
|
(state) => state.settings.advancedSettings,
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.metadataProfiles,
|
(state) => state.settings.metadataProfiles,
|
||||||
createProviderSettingsSelector('importLists'),
|
createProviderSettingsSelector('importLists'),
|
||||||
(advancedSettings, languageProfiles, metadataProfiles, importList) => {
|
(advancedSettings, metadataProfiles, importList) => {
|
||||||
return {
|
return {
|
||||||
advancedSettings,
|
advancedSettings,
|
||||||
showLanguageProfile: languageProfiles.items.length > 1,
|
|
||||||
showMetadataProfile: metadataProfiles.items.length > 1,
|
showMetadataProfile: metadataProfiles.items.length > 1,
|
||||||
...importList
|
...importList
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,27 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React from 'react';
|
|
||||||
import { sizes } from 'Helpers/Props';
|
|
||||||
import Modal from 'Components/Modal/Modal';
|
|
||||||
import EditLanguageProfileModalContentConnector from './EditLanguageProfileModalContentConnector';
|
|
||||||
|
|
||||||
function EditLanguageProfileModal({ isOpen, onModalClose, ...otherProps }) {
|
|
||||||
return (
|
|
||||||
<Modal
|
|
||||||
size={sizes.MEDIUM}
|
|
||||||
isOpen={isOpen}
|
|
||||||
onModalClose={onModalClose}
|
|
||||||
>
|
|
||||||
<EditLanguageProfileModalContentConnector
|
|
||||||
{...otherProps}
|
|
||||||
onModalClose={onModalClose}
|
|
||||||
/>
|
|
||||||
</Modal>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
EditLanguageProfileModal.propTypes = {
|
|
||||||
isOpen: PropTypes.bool.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default EditLanguageProfileModal;
|
|
|
@ -1,43 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { clearPendingChanges } from 'Store/Actions/baseActions';
|
|
||||||
import EditLanguageProfileModal from './EditLanguageProfileModal';
|
|
||||||
|
|
||||||
function mapStateToProps() {
|
|
||||||
return {};
|
|
||||||
}
|
|
||||||
|
|
||||||
const mapDispatchToProps = {
|
|
||||||
clearPendingChanges
|
|
||||||
};
|
|
||||||
|
|
||||||
class EditLanguageProfileModalConnector extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onModalClose = () => {
|
|
||||||
this.props.clearPendingChanges({ section: 'settings.languageProfiles' });
|
|
||||||
this.props.onModalClose();
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
return (
|
|
||||||
<EditLanguageProfileModal
|
|
||||||
{...this.props}
|
|
||||||
onModalClose={this.onModalClose}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
EditLanguageProfileModalConnector.propTypes = {
|
|
||||||
onModalClose: PropTypes.func.isRequired,
|
|
||||||
clearPendingChanges: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(mapStateToProps, mapDispatchToProps)(EditLanguageProfileModalConnector);
|
|
|
@ -1,3 +0,0 @@
|
||||||
.deleteButtonContainer {
|
|
||||||
margin-right: auto;
|
|
||||||
}
|
|
|
@ -1,165 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React from 'react';
|
|
||||||
import { inputTypes, kinds } from 'Helpers/Props';
|
|
||||||
import Button from 'Components/Link/Button';
|
|
||||||
import SpinnerErrorButton from 'Components/Link/SpinnerErrorButton';
|
|
||||||
import LoadingIndicator from 'Components/Loading/LoadingIndicator';
|
|
||||||
import ModalContent from 'Components/Modal/ModalContent';
|
|
||||||
import ModalHeader from 'Components/Modal/ModalHeader';
|
|
||||||
import ModalBody from 'Components/Modal/ModalBody';
|
|
||||||
import ModalFooter from 'Components/Modal/ModalFooter';
|
|
||||||
import Form from 'Components/Form/Form';
|
|
||||||
import FormGroup from 'Components/Form/FormGroup';
|
|
||||||
import FormLabel from 'Components/Form/FormLabel';
|
|
||||||
import FormInputGroup from 'Components/Form/FormInputGroup';
|
|
||||||
import LanguageProfileItems from './LanguageProfileItems';
|
|
||||||
import styles from './EditLanguageProfileModalContent.css';
|
|
||||||
|
|
||||||
function EditLanguageProfileModalContent(props) {
|
|
||||||
const {
|
|
||||||
isFetching,
|
|
||||||
error,
|
|
||||||
isSaving,
|
|
||||||
saveError,
|
|
||||||
languages,
|
|
||||||
item,
|
|
||||||
isInUse,
|
|
||||||
onInputChange,
|
|
||||||
onCutoffChange,
|
|
||||||
onSavePress,
|
|
||||||
onModalClose,
|
|
||||||
onDeleteLanguageProfilePress,
|
|
||||||
...otherProps
|
|
||||||
} = props;
|
|
||||||
|
|
||||||
const {
|
|
||||||
id,
|
|
||||||
name,
|
|
||||||
upgradeAllowed,
|
|
||||||
cutoff,
|
|
||||||
languages: itemLanguages
|
|
||||||
} = item;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<ModalContent onModalClose={onModalClose}>
|
|
||||||
<ModalHeader>
|
|
||||||
{id ? 'Edit Language Profile' : 'Add Language Profile'}
|
|
||||||
</ModalHeader>
|
|
||||||
|
|
||||||
<ModalBody>
|
|
||||||
{
|
|
||||||
isFetching &&
|
|
||||||
<LoadingIndicator />
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
!isFetching && !!error &&
|
|
||||||
<div>Unable to add a new language profile, please try again.</div>
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
!isFetching && !error &&
|
|
||||||
<Form {...otherProps}>
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>Name</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.TEXT}
|
|
||||||
name="name"
|
|
||||||
{...name}
|
|
||||||
onChange={onInputChange}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>
|
|
||||||
Upgrades Allowed
|
|
||||||
</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.CHECK}
|
|
||||||
name="upgradeAllowed"
|
|
||||||
{...upgradeAllowed}
|
|
||||||
helpText="If disabled languages will not be upgraded"
|
|
||||||
onChange={onInputChange}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
|
|
||||||
{
|
|
||||||
upgradeAllowed.value &&
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>Upgrade Until</FormLabel>
|
|
||||||
|
|
||||||
<FormInputGroup
|
|
||||||
type={inputTypes.SELECT}
|
|
||||||
name="cutoff"
|
|
||||||
{...cutoff}
|
|
||||||
value={cutoff ? cutoff.value.id : 0}
|
|
||||||
values={languages}
|
|
||||||
helpText="Once this language is reached Lidarr will no longer download albums"
|
|
||||||
onChange={onCutoffChange}
|
|
||||||
/>
|
|
||||||
</FormGroup>
|
|
||||||
}
|
|
||||||
|
|
||||||
<LanguageProfileItems
|
|
||||||
languageProfileItems={itemLanguages.value}
|
|
||||||
errors={itemLanguages.errors}
|
|
||||||
warnings={itemLanguages.warnings}
|
|
||||||
{...otherProps}
|
|
||||||
/>
|
|
||||||
|
|
||||||
</Form>
|
|
||||||
}
|
|
||||||
</ModalBody>
|
|
||||||
<ModalFooter>
|
|
||||||
{
|
|
||||||
id &&
|
|
||||||
<div
|
|
||||||
className={styles.deleteButtonContainer}
|
|
||||||
title={isInUse ? 'Can\'t delete a language profile that is attached to an artist or import list' : undefined}
|
|
||||||
>
|
|
||||||
<Button
|
|
||||||
kind={kinds.DANGER}
|
|
||||||
isDisabled={isInUse}
|
|
||||||
onPress={onDeleteLanguageProfilePress}
|
|
||||||
>
|
|
||||||
Delete
|
|
||||||
</Button>
|
|
||||||
</div>
|
|
||||||
}
|
|
||||||
|
|
||||||
<Button
|
|
||||||
onPress={onModalClose}
|
|
||||||
>
|
|
||||||
Cancel
|
|
||||||
</Button>
|
|
||||||
|
|
||||||
<SpinnerErrorButton
|
|
||||||
isSpinning={isSaving}
|
|
||||||
error={saveError}
|
|
||||||
onPress={onSavePress}
|
|
||||||
>
|
|
||||||
Save
|
|
||||||
</SpinnerErrorButton>
|
|
||||||
</ModalFooter>
|
|
||||||
</ModalContent>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
EditLanguageProfileModalContent.propTypes = {
|
|
||||||
isFetching: PropTypes.bool.isRequired,
|
|
||||||
error: PropTypes.object,
|
|
||||||
isSaving: PropTypes.bool.isRequired,
|
|
||||||
saveError: PropTypes.object,
|
|
||||||
languages: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
item: PropTypes.object.isRequired,
|
|
||||||
isInUse: PropTypes.bool.isRequired,
|
|
||||||
onInputChange: PropTypes.func.isRequired,
|
|
||||||
onCutoffChange: PropTypes.func.isRequired,
|
|
||||||
onSavePress: PropTypes.func.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired,
|
|
||||||
onDeleteLanguageProfilePress: PropTypes.func
|
|
||||||
};
|
|
||||||
|
|
||||||
export default EditLanguageProfileModalContent;
|
|
|
@ -1,189 +0,0 @@
|
||||||
import _ from 'lodash';
|
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import createProfileInUseSelector from 'Store/Selectors/createProfileInUseSelector';
|
|
||||||
import createProviderSettingsSelector from 'Store/Selectors/createProviderSettingsSelector';
|
|
||||||
import { fetchLanguageProfileSchema, setLanguageProfileValue, saveLanguageProfile } from 'Store/Actions/settingsActions';
|
|
||||||
import EditLanguageProfileModalContent from './EditLanguageProfileModalContent';
|
|
||||||
|
|
||||||
function createLanguagesSelector() {
|
|
||||||
return createSelector(
|
|
||||||
createProviderSettingsSelector('languageProfiles'),
|
|
||||||
(languageProfile) => {
|
|
||||||
const languages = languageProfile.item.languages;
|
|
||||||
if (!languages || !languages.value) {
|
|
||||||
return [];
|
|
||||||
}
|
|
||||||
|
|
||||||
return _.reduceRight(languages.value, (result, { allowed, language }) => {
|
|
||||||
if (allowed) {
|
|
||||||
result.push({
|
|
||||||
key: language.id,
|
|
||||||
value: language.name
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}, []);
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
createProviderSettingsSelector('languageProfiles'),
|
|
||||||
createLanguagesSelector(),
|
|
||||||
createProfileInUseSelector('languageProfileId'),
|
|
||||||
(languageProfile, languages, isInUse) => {
|
|
||||||
return {
|
|
||||||
languages,
|
|
||||||
...languageProfile,
|
|
||||||
isInUse
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
const mapDispatchToProps = {
|
|
||||||
fetchLanguageProfileSchema,
|
|
||||||
setLanguageProfileValue,
|
|
||||||
saveLanguageProfile
|
|
||||||
};
|
|
||||||
|
|
||||||
class EditLanguageProfileModalContentConnector extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
constructor(props, context) {
|
|
||||||
super(props, context);
|
|
||||||
|
|
||||||
this.state = {
|
|
||||||
dragIndex: null,
|
|
||||||
dropIndex: null
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
componentDidMount() {
|
|
||||||
if (!this.props.id && !this.props.isPopulated) {
|
|
||||||
this.props.fetchLanguageProfileSchema();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
componentDidUpdate(prevProps, prevState) {
|
|
||||||
if (prevProps.isSaving && !this.props.isSaving && !this.props.saveError) {
|
|
||||||
this.props.onModalClose();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onInputChange = ({ name, value }) => {
|
|
||||||
this.props.setLanguageProfileValue({ name, value });
|
|
||||||
}
|
|
||||||
|
|
||||||
onCutoffChange = ({ name, value }) => {
|
|
||||||
const id = parseInt(value);
|
|
||||||
const item = _.find(this.props.item.languages.value, (i) => i.language.id === id);
|
|
||||||
|
|
||||||
this.props.setLanguageProfileValue({ name, value: item.language });
|
|
||||||
}
|
|
||||||
|
|
||||||
onSavePress = () => {
|
|
||||||
this.props.saveLanguageProfile({ id: this.props.id });
|
|
||||||
}
|
|
||||||
|
|
||||||
onLanguageProfileItemAllowedChange = (id, allowed) => {
|
|
||||||
const languageProfile = _.cloneDeep(this.props.item);
|
|
||||||
|
|
||||||
const item = _.find(languageProfile.languages.value, (i) => i.language.id === id);
|
|
||||||
item.allowed = allowed;
|
|
||||||
|
|
||||||
this.props.setLanguageProfileValue({
|
|
||||||
name: 'languages',
|
|
||||||
value: languageProfile.languages.value
|
|
||||||
});
|
|
||||||
|
|
||||||
const cutoff = languageProfile.cutoff.value;
|
|
||||||
|
|
||||||
// If the cutoff isn't allowed anymore or there isn't a cutoff set one
|
|
||||||
if (!cutoff || !_.find(languageProfile.languages.value, (i) => i.language.id === cutoff.id).allowed) {
|
|
||||||
const firstAllowed = _.find(languageProfile.languages.value, { allowed: true });
|
|
||||||
|
|
||||||
this.props.setLanguageProfileValue({ name: 'cutoff', value: firstAllowed ? firstAllowed.language : null });
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
onLanguageProfileItemDragMove = (dragIndex, dropIndex) => {
|
|
||||||
if (this.state.dragIndex !== dragIndex || this.state.dropIndex !== dropIndex) {
|
|
||||||
this.setState({
|
|
||||||
dragIndex,
|
|
||||||
dropIndex
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
onLanguageProfileItemDragEnd = ({ id }, didDrop) => {
|
|
||||||
const {
|
|
||||||
dragIndex,
|
|
||||||
dropIndex
|
|
||||||
} = this.state;
|
|
||||||
|
|
||||||
if (didDrop && dropIndex !== null) {
|
|
||||||
const languageProfile = _.cloneDeep(this.props.item);
|
|
||||||
|
|
||||||
const languages = languageProfile.languages.value.splice(dragIndex, 1);
|
|
||||||
languageProfile.languages.value.splice(dropIndex, 0, languages[0]);
|
|
||||||
|
|
||||||
this.props.setLanguageProfileValue({
|
|
||||||
name: 'languages',
|
|
||||||
value: languageProfile.languages.value
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
this.setState({
|
|
||||||
dragIndex: null,
|
|
||||||
dropIndex: null
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
if (_.isEmpty(this.props.item.languages) && !this.props.isFetching) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
|
||||||
<EditLanguageProfileModalContent
|
|
||||||
{...this.state}
|
|
||||||
{...this.props}
|
|
||||||
onSavePress={this.onSavePress}
|
|
||||||
onInputChange={this.onInputChange}
|
|
||||||
onCutoffChange={this.onCutoffChange}
|
|
||||||
onLanguageProfileItemAllowedChange={this.onLanguageProfileItemAllowedChange}
|
|
||||||
onLanguageProfileItemDragMove={this.onLanguageProfileItemDragMove}
|
|
||||||
onLanguageProfileItemDragEnd={this.onLanguageProfileItemDragEnd}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
EditLanguageProfileModalContentConnector.propTypes = {
|
|
||||||
id: PropTypes.number,
|
|
||||||
isFetching: PropTypes.bool.isRequired,
|
|
||||||
isPopulated: PropTypes.bool.isRequired,
|
|
||||||
isSaving: PropTypes.bool.isRequired,
|
|
||||||
saveError: PropTypes.object,
|
|
||||||
item: PropTypes.object.isRequired,
|
|
||||||
setLanguageProfileValue: PropTypes.func.isRequired,
|
|
||||||
fetchLanguageProfileSchema: PropTypes.func.isRequired,
|
|
||||||
saveLanguageProfile: PropTypes.func.isRequired,
|
|
||||||
onModalClose: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps, mapDispatchToProps)(EditLanguageProfileModalContentConnector);
|
|
|
@ -1,31 +0,0 @@
|
||||||
.languageProfile {
|
|
||||||
composes: card from '~Components/Card.css';
|
|
||||||
|
|
||||||
width: 300px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.nameContainer {
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-between;
|
|
||||||
}
|
|
||||||
|
|
||||||
.name {
|
|
||||||
@add-mixin truncate;
|
|
||||||
|
|
||||||
margin-bottom: 20px;
|
|
||||||
font-weight: 300;
|
|
||||||
font-size: 24px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.cloneButton {
|
|
||||||
composes: button from '~Components/Link/IconButton.css';
|
|
||||||
|
|
||||||
height: 36px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.languages {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
margin-top: 5px;
|
|
||||||
pointer-events: all;
|
|
||||||
}
|
|
|
@ -1,147 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { icons, kinds } from 'Helpers/Props';
|
|
||||||
import Card from 'Components/Card';
|
|
||||||
import Label from 'Components/Label';
|
|
||||||
import IconButton from 'Components/Link/IconButton';
|
|
||||||
import ConfirmModal from 'Components/Modal/ConfirmModal';
|
|
||||||
import EditLanguageProfileModalConnector from './EditLanguageProfileModalConnector';
|
|
||||||
import styles from './LanguageProfile.css';
|
|
||||||
|
|
||||||
class LanguageProfile extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
constructor(props, context) {
|
|
||||||
super(props, context);
|
|
||||||
|
|
||||||
this.state = {
|
|
||||||
isEditLanguageProfileModalOpen: false,
|
|
||||||
isDeleteLanguageProfileModalOpen: false
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onEditLanguageProfilePress = () => {
|
|
||||||
this.setState({ isEditLanguageProfileModalOpen: true });
|
|
||||||
}
|
|
||||||
|
|
||||||
onEditLanguageProfileModalClose = () => {
|
|
||||||
this.setState({ isEditLanguageProfileModalOpen: false });
|
|
||||||
}
|
|
||||||
|
|
||||||
onDeleteLanguageProfilePress = () => {
|
|
||||||
this.setState({
|
|
||||||
isEditLanguageProfileModalOpen: false,
|
|
||||||
isDeleteLanguageProfileModalOpen: true
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
onDeleteLanguageProfileModalClose = () => {
|
|
||||||
this.setState({ isDeleteLanguageProfileModalOpen: false });
|
|
||||||
}
|
|
||||||
|
|
||||||
onConfirmDeleteLanguageProfile = () => {
|
|
||||||
this.props.onConfirmDeleteLanguageProfile(this.props.id);
|
|
||||||
}
|
|
||||||
|
|
||||||
onCloneLanguageProfilePress = () => {
|
|
||||||
const {
|
|
||||||
id,
|
|
||||||
onCloneLanguageProfilePress
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
onCloneLanguageProfilePress(id);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
id,
|
|
||||||
name,
|
|
||||||
upgradeAllowed,
|
|
||||||
cutoff,
|
|
||||||
languages,
|
|
||||||
isDeleting
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Card
|
|
||||||
className={styles.languageProfile}
|
|
||||||
overlayContent={true}
|
|
||||||
onPress={this.onEditLanguageProfilePress}
|
|
||||||
>
|
|
||||||
<div className={styles.nameContainer}>
|
|
||||||
<div className={styles.name}>
|
|
||||||
{name}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<IconButton
|
|
||||||
className={styles.cloneButton}
|
|
||||||
title="Clone Profile"
|
|
||||||
name={icons.CLONE}
|
|
||||||
onPress={this.onCloneLanguageProfilePress}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div className={styles.languages}>
|
|
||||||
{
|
|
||||||
languages.map((item) => {
|
|
||||||
if (!item.allowed) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
const isCutoff = upgradeAllowed && item.language.id === cutoff.id;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<Label
|
|
||||||
key={item.language.id}
|
|
||||||
kind={isCutoff ? kinds.INFO : kinds.default}
|
|
||||||
title={isCutoff ? 'Upgrade until this language is met or exceeded' : null}
|
|
||||||
>
|
|
||||||
{item.language.name}
|
|
||||||
</Label>
|
|
||||||
);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<EditLanguageProfileModalConnector
|
|
||||||
id={id}
|
|
||||||
isOpen={this.state.isEditLanguageProfileModalOpen}
|
|
||||||
onModalClose={this.onEditLanguageProfileModalClose}
|
|
||||||
onDeleteLanguageProfilePress={this.onDeleteLanguageProfilePress}
|
|
||||||
/>
|
|
||||||
|
|
||||||
<ConfirmModal
|
|
||||||
isOpen={this.state.isDeleteLanguageProfileModalOpen}
|
|
||||||
kind={kinds.DANGER}
|
|
||||||
title="Delete Language Profile"
|
|
||||||
message={`Are you sure you want to delete the language profile '${name}'?`}
|
|
||||||
confirmLabel="Delete"
|
|
||||||
isSpinning={isDeleting}
|
|
||||||
onConfirm={this.onConfirmDeleteLanguageProfile}
|
|
||||||
onCancel={this.onDeleteLanguageProfileModalClose}
|
|
||||||
/>
|
|
||||||
</Card>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfile.propTypes = {
|
|
||||||
id: PropTypes.number.isRequired,
|
|
||||||
name: PropTypes.string.isRequired,
|
|
||||||
upgradeAllowed: PropTypes.bool.isRequired,
|
|
||||||
cutoff: PropTypes.object.isRequired,
|
|
||||||
languages: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
isDeleting: PropTypes.bool.isRequired,
|
|
||||||
onConfirmDeleteLanguageProfile: PropTypes.func.isRequired,
|
|
||||||
onCloneLanguageProfilePress: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default LanguageProfile;
|
|
|
@ -1,44 +0,0 @@
|
||||||
.languageProfileItem {
|
|
||||||
display: flex;
|
|
||||||
align-items: stretch;
|
|
||||||
width: 100%;
|
|
||||||
border: 1px solid #aaa;
|
|
||||||
border-radius: 4px;
|
|
||||||
background: #fafafa;
|
|
||||||
}
|
|
||||||
|
|
||||||
.checkContainer {
|
|
||||||
position: relative;
|
|
||||||
margin-right: 4px;
|
|
||||||
margin-bottom: 7px;
|
|
||||||
margin-left: 8px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.languageName {
|
|
||||||
display: flex;
|
|
||||||
flex-grow: 1;
|
|
||||||
margin-bottom: 0;
|
|
||||||
margin-left: 2px;
|
|
||||||
font-weight: normal;
|
|
||||||
line-height: 36px;
|
|
||||||
cursor: pointer;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dragHandle {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: center;
|
|
||||||
flex-shrink: 0;
|
|
||||||
margin-left: auto;
|
|
||||||
width: $dragHandleWidth;
|
|
||||||
text-align: center;
|
|
||||||
cursor: grab;
|
|
||||||
}
|
|
||||||
|
|
||||||
.dragIcon {
|
|
||||||
top: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.isDragging {
|
|
||||||
opacity: 0.25;
|
|
||||||
}
|
|
|
@ -1,83 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import classNames from 'classnames';
|
|
||||||
import { icons } from 'Helpers/Props';
|
|
||||||
import Icon from 'Components/Icon';
|
|
||||||
import CheckInput from 'Components/Form/CheckInput';
|
|
||||||
import styles from './LanguageProfileItem.css';
|
|
||||||
|
|
||||||
class LanguageProfileItem extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onAllowedChange = ({ value }) => {
|
|
||||||
const {
|
|
||||||
languageId,
|
|
||||||
onLanguageProfileItemAllowedChange
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
onLanguageProfileItemAllowedChange(languageId, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
name,
|
|
||||||
allowed,
|
|
||||||
isDragging,
|
|
||||||
connectDragSource
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<div
|
|
||||||
className={classNames(
|
|
||||||
styles.languageProfileItem,
|
|
||||||
isDragging && styles.isDragging,
|
|
||||||
)}
|
|
||||||
>
|
|
||||||
<label
|
|
||||||
className={styles.languageName}
|
|
||||||
>
|
|
||||||
<CheckInput
|
|
||||||
containerClassName={styles.checkContainer}
|
|
||||||
name={name}
|
|
||||||
value={allowed}
|
|
||||||
onChange={this.onAllowedChange}
|
|
||||||
/>
|
|
||||||
{name}
|
|
||||||
</label>
|
|
||||||
|
|
||||||
{
|
|
||||||
connectDragSource(
|
|
||||||
<div className={styles.dragHandle}>
|
|
||||||
<Icon
|
|
||||||
className={styles.dragIcon}
|
|
||||||
name={icons.REORDER}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
)
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileItem.propTypes = {
|
|
||||||
languageId: PropTypes.number.isRequired,
|
|
||||||
name: PropTypes.string.isRequired,
|
|
||||||
allowed: PropTypes.bool.isRequired,
|
|
||||||
sortIndex: PropTypes.number.isRequired,
|
|
||||||
isDragging: PropTypes.bool.isRequired,
|
|
||||||
connectDragSource: PropTypes.func,
|
|
||||||
onLanguageProfileItemAllowedChange: PropTypes.func
|
|
||||||
};
|
|
||||||
|
|
||||||
LanguageProfileItem.defaultProps = {
|
|
||||||
// The drag preview will not connect the drag handle.
|
|
||||||
connectDragSource: (node) => node
|
|
||||||
};
|
|
||||||
|
|
||||||
export default LanguageProfileItem;
|
|
|
@ -1,4 +0,0 @@
|
||||||
.dragPreview {
|
|
||||||
width: 380px;
|
|
||||||
opacity: 0.75;
|
|
||||||
}
|
|
|
@ -1,90 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { DragLayer } from 'react-dnd';
|
|
||||||
import dimensions from 'Styles/Variables/dimensions.js';
|
|
||||||
import { QUALITY_PROFILE_ITEM } from 'Helpers/dragTypes';
|
|
||||||
import DragPreviewLayer from 'Components/DragPreviewLayer';
|
|
||||||
import LanguageProfileItem from './LanguageProfileItem';
|
|
||||||
import styles from './LanguageProfileItemDragPreview.css';
|
|
||||||
|
|
||||||
const formGroupSmallWidth = parseInt(dimensions.formGroupSmallWidth);
|
|
||||||
const formLabelLargeWidth = parseInt(dimensions.formLabelLargeWidth);
|
|
||||||
const formLabelRightMarginWidth = parseInt(dimensions.formLabelRightMarginWidth);
|
|
||||||
const dragHandleWidth = parseInt(dimensions.dragHandleWidth);
|
|
||||||
|
|
||||||
function collectDragLayer(monitor) {
|
|
||||||
return {
|
|
||||||
item: monitor.getItem(),
|
|
||||||
itemType: monitor.getItemType(),
|
|
||||||
currentOffset: monitor.getSourceClientOffset()
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
class LanguageProfileItemDragPreview extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
item,
|
|
||||||
itemType,
|
|
||||||
currentOffset
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
if (!currentOffset || itemType !== QUALITY_PROFILE_ITEM) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// The offset is shifted because the drag handle is on the right edge of the
|
|
||||||
// list item and the preview is wider than the drag handle.
|
|
||||||
|
|
||||||
const { x, y } = currentOffset;
|
|
||||||
const handleOffset = formGroupSmallWidth - formLabelLargeWidth - formLabelRightMarginWidth - dragHandleWidth;
|
|
||||||
const transform = `translate3d(${x - handleOffset}px, ${y}px, 0)`;
|
|
||||||
|
|
||||||
const style = {
|
|
||||||
position: 'absolute',
|
|
||||||
WebkitTransform: transform,
|
|
||||||
msTransform: transform,
|
|
||||||
transform
|
|
||||||
};
|
|
||||||
|
|
||||||
const {
|
|
||||||
languageId,
|
|
||||||
name,
|
|
||||||
allowed,
|
|
||||||
sortIndex
|
|
||||||
} = item;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<DragPreviewLayer>
|
|
||||||
<div
|
|
||||||
className={styles.dragPreview}
|
|
||||||
style={style}
|
|
||||||
>
|
|
||||||
<LanguageProfileItem
|
|
||||||
languageId={languageId}
|
|
||||||
name={name}
|
|
||||||
allowed={allowed}
|
|
||||||
sortIndex={sortIndex}
|
|
||||||
isDragging={false}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</DragPreviewLayer>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileItemDragPreview.propTypes = {
|
|
||||||
item: PropTypes.object,
|
|
||||||
itemType: PropTypes.string,
|
|
||||||
currentOffset: PropTypes.shape({
|
|
||||||
x: PropTypes.number.isRequired,
|
|
||||||
y: PropTypes.number.isRequired
|
|
||||||
})
|
|
||||||
};
|
|
||||||
|
|
||||||
/* eslint-disable new-cap */
|
|
||||||
export default DragLayer(collectDragLayer)(LanguageProfileItemDragPreview);
|
|
||||||
/* eslint-enable new-cap */
|
|
|
@ -1,18 +0,0 @@
|
||||||
.languageProfileItemDragSource {
|
|
||||||
padding: 4px 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.languageProfileItemPlaceholder {
|
|
||||||
width: 100%;
|
|
||||||
height: 36px;
|
|
||||||
border: 1px dotted #aaa;
|
|
||||||
border-radius: 4px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.languageProfileItemPlaceholderBefore {
|
|
||||||
margin-bottom: 8px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.languageProfileItemPlaceholderAfter {
|
|
||||||
margin-top: 8px;
|
|
||||||
}
|
|
|
@ -1,159 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { findDOMNode } from 'react-dom';
|
|
||||||
import { DragSource, DropTarget } from 'react-dnd';
|
|
||||||
import classNames from 'classnames';
|
|
||||||
import { QUALITY_PROFILE_ITEM } from 'Helpers/dragTypes';
|
|
||||||
import LanguageProfileItem from './LanguageProfileItem';
|
|
||||||
import styles from './LanguageProfileItemDragSource.css';
|
|
||||||
|
|
||||||
const languageProfileItemDragSource = {
|
|
||||||
beginDrag({ languageId, name, allowed, sortIndex }) {
|
|
||||||
return {
|
|
||||||
languageId,
|
|
||||||
name,
|
|
||||||
allowed,
|
|
||||||
sortIndex
|
|
||||||
};
|
|
||||||
},
|
|
||||||
|
|
||||||
endDrag(props, monitor, component) {
|
|
||||||
props.onLanguageProfileItemDragEnd(monitor.getItem(), monitor.didDrop());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
const languageProfileItemDropTarget = {
|
|
||||||
hover(props, monitor, component) {
|
|
||||||
const dragIndex = monitor.getItem().sortIndex;
|
|
||||||
const hoverIndex = props.sortIndex;
|
|
||||||
|
|
||||||
const hoverBoundingRect = findDOMNode(component).getBoundingClientRect();
|
|
||||||
const hoverMiddleY = (hoverBoundingRect.bottom - hoverBoundingRect.top) / 2;
|
|
||||||
const clientOffset = monitor.getClientOffset();
|
|
||||||
const hoverClientY = clientOffset.y - hoverBoundingRect.top;
|
|
||||||
|
|
||||||
// Moving up, only trigger if drag position is above 50%
|
|
||||||
if (dragIndex < hoverIndex && hoverClientY > hoverMiddleY) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Moving down, only trigger if drag position is below 50%
|
|
||||||
if (dragIndex > hoverIndex && hoverClientY < hoverMiddleY) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
props.onLanguageProfileItemDragMove(dragIndex, hoverIndex);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
function collectDragSource(connect, monitor) {
|
|
||||||
return {
|
|
||||||
connectDragSource: connect.dragSource(),
|
|
||||||
isDragging: monitor.isDragging()
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
function collectDropTarget(connect, monitor) {
|
|
||||||
return {
|
|
||||||
connectDropTarget: connect.dropTarget(),
|
|
||||||
isOver: monitor.isOver()
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
class LanguageProfileItemDragSource extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
languageId,
|
|
||||||
name,
|
|
||||||
allowed,
|
|
||||||
sortIndex,
|
|
||||||
isDragging,
|
|
||||||
isDraggingUp,
|
|
||||||
isDraggingDown,
|
|
||||||
isOver,
|
|
||||||
connectDragSource,
|
|
||||||
connectDropTarget,
|
|
||||||
onLanguageProfileItemAllowedChange
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
const isBefore = !isDragging && isDraggingUp && isOver;
|
|
||||||
const isAfter = !isDragging && isDraggingDown && isOver;
|
|
||||||
|
|
||||||
// if (isDragging && !isOver) {
|
|
||||||
// return null;
|
|
||||||
// }
|
|
||||||
|
|
||||||
return connectDropTarget(
|
|
||||||
<div
|
|
||||||
className={classNames(
|
|
||||||
styles.languageProfileItemDragSource,
|
|
||||||
isBefore && styles.isDraggingUp,
|
|
||||||
isAfter && styles.isDraggingDown
|
|
||||||
)}
|
|
||||||
>
|
|
||||||
{
|
|
||||||
isBefore &&
|
|
||||||
<div
|
|
||||||
className={classNames(
|
|
||||||
styles.languageProfileItemPlaceholder,
|
|
||||||
styles.languageProfileItemPlaceholderBefore
|
|
||||||
)}
|
|
||||||
/>
|
|
||||||
}
|
|
||||||
|
|
||||||
<LanguageProfileItem
|
|
||||||
languageId={languageId}
|
|
||||||
name={name}
|
|
||||||
allowed={allowed}
|
|
||||||
sortIndex={sortIndex}
|
|
||||||
isDragging={isDragging}
|
|
||||||
isOver={isOver}
|
|
||||||
connectDragSource={connectDragSource}
|
|
||||||
onLanguageProfileItemAllowedChange={onLanguageProfileItemAllowedChange}
|
|
||||||
/>
|
|
||||||
|
|
||||||
{
|
|
||||||
isAfter &&
|
|
||||||
<div
|
|
||||||
className={classNames(
|
|
||||||
styles.languageProfileItemPlaceholder,
|
|
||||||
styles.languageProfileItemPlaceholderAfter
|
|
||||||
)}
|
|
||||||
/>
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileItemDragSource.propTypes = {
|
|
||||||
languageId: PropTypes.number.isRequired,
|
|
||||||
name: PropTypes.string.isRequired,
|
|
||||||
allowed: PropTypes.bool.isRequired,
|
|
||||||
sortIndex: PropTypes.number.isRequired,
|
|
||||||
isDragging: PropTypes.bool,
|
|
||||||
isDraggingUp: PropTypes.bool,
|
|
||||||
isDraggingDown: PropTypes.bool,
|
|
||||||
isOver: PropTypes.bool,
|
|
||||||
connectDragSource: PropTypes.func,
|
|
||||||
connectDropTarget: PropTypes.func,
|
|
||||||
onLanguageProfileItemAllowedChange: PropTypes.func.isRequired,
|
|
||||||
onLanguageProfileItemDragMove: PropTypes.func.isRequired,
|
|
||||||
onLanguageProfileItemDragEnd: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
/* eslint-disable new-cap */
|
|
||||||
export default DropTarget(
|
|
||||||
QUALITY_PROFILE_ITEM,
|
|
||||||
languageProfileItemDropTarget,
|
|
||||||
collectDropTarget
|
|
||||||
)(DragSource(
|
|
||||||
QUALITY_PROFILE_ITEM,
|
|
||||||
languageProfileItemDragSource,
|
|
||||||
collectDragSource
|
|
||||||
)(LanguageProfileItemDragSource));
|
|
||||||
/* eslint-enable new-cap */
|
|
|
@ -1,6 +0,0 @@
|
||||||
.languages {
|
|
||||||
margin-top: 10px;
|
|
||||||
/* TODO: This should consider the number of languages in the list */
|
|
||||||
min-height: 550px;
|
|
||||||
user-select: none;
|
|
||||||
}
|
|
|
@ -1,103 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import FormGroup from 'Components/Form/FormGroup';
|
|
||||||
import FormLabel from 'Components/Form/FormLabel';
|
|
||||||
import FormInputHelpText from 'Components/Form/FormInputHelpText';
|
|
||||||
import LanguageProfileItemDragSource from './LanguageProfileItemDragSource';
|
|
||||||
import LanguageProfileItemDragPreview from './LanguageProfileItemDragPreview';
|
|
||||||
import styles from './LanguageProfileItems.css';
|
|
||||||
|
|
||||||
class LanguageProfileItems extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
dragIndex,
|
|
||||||
dropIndex,
|
|
||||||
languageProfileItems,
|
|
||||||
errors,
|
|
||||||
warnings,
|
|
||||||
...otherProps
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
const isDragging = dropIndex !== null;
|
|
||||||
const isDraggingUp = isDragging && dropIndex > dragIndex;
|
|
||||||
const isDraggingDown = isDragging && dropIndex < dragIndex;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<FormGroup>
|
|
||||||
<FormLabel>Languages</FormLabel>
|
|
||||||
<div>
|
|
||||||
<FormInputHelpText
|
|
||||||
text="Languages higher in the list are more preferred. Only checked languages are wanted"
|
|
||||||
/>
|
|
||||||
|
|
||||||
{
|
|
||||||
errors.map((error, index) => {
|
|
||||||
return (
|
|
||||||
<FormInputHelpText
|
|
||||||
key={index}
|
|
||||||
text={error.message}
|
|
||||||
isError={true}
|
|
||||||
isCheckInput={false}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
{
|
|
||||||
warnings.map((warning, index) => {
|
|
||||||
return (
|
|
||||||
<FormInputHelpText
|
|
||||||
key={index}
|
|
||||||
text={warning.message}
|
|
||||||
isWarning={true}
|
|
||||||
isCheckInput={false}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
<div className={styles.languages}>
|
|
||||||
{
|
|
||||||
languageProfileItems.map(({ allowed, language }, index) => {
|
|
||||||
return (
|
|
||||||
<LanguageProfileItemDragSource
|
|
||||||
key={language.id}
|
|
||||||
languageId={language.id}
|
|
||||||
name={language.name}
|
|
||||||
allowed={allowed}
|
|
||||||
sortIndex={index}
|
|
||||||
isDragging={isDragging}
|
|
||||||
isDraggingUp={isDraggingUp}
|
|
||||||
isDraggingDown={isDraggingDown}
|
|
||||||
{...otherProps}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}).reverse()
|
|
||||||
}
|
|
||||||
|
|
||||||
<LanguageProfileItemDragPreview />
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</FormGroup>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileItems.propTypes = {
|
|
||||||
dragIndex: PropTypes.number,
|
|
||||||
dropIndex: PropTypes.number,
|
|
||||||
languageProfileItems: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
errors: PropTypes.arrayOf(PropTypes.object),
|
|
||||||
warnings: PropTypes.arrayOf(PropTypes.object)
|
|
||||||
};
|
|
||||||
|
|
||||||
LanguageProfileItems.defaultProps = {
|
|
||||||
errors: [],
|
|
||||||
warnings: []
|
|
||||||
};
|
|
||||||
|
|
||||||
export default LanguageProfileItems;
|
|
|
@ -1,31 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import createLanguageProfileSelector from 'Store/Selectors/createLanguageProfileSelector';
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
createLanguageProfileSelector(),
|
|
||||||
(languageProfile) => {
|
|
||||||
return {
|
|
||||||
name: languageProfile.name
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
function LanguageProfileNameConnector({ name, ...otherProps }) {
|
|
||||||
return (
|
|
||||||
<span>
|
|
||||||
{name}
|
|
||||||
</span>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfileNameConnector.propTypes = {
|
|
||||||
languageProfileId: PropTypes.number.isRequired,
|
|
||||||
name: PropTypes.string.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps)(LanguageProfileNameConnector);
|
|
|
@ -1,21 +0,0 @@
|
||||||
.languageProfiles {
|
|
||||||
display: flex;
|
|
||||||
flex-wrap: wrap;
|
|
||||||
}
|
|
||||||
|
|
||||||
.addLanguageProfile {
|
|
||||||
composes: languageProfile from '~./LanguageProfile.css';
|
|
||||||
|
|
||||||
background-color: $cardAlternateBackgroundColor;
|
|
||||||
color: $gray;
|
|
||||||
text-align: center;
|
|
||||||
font-size: 45px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.center {
|
|
||||||
display: inline-block;
|
|
||||||
padding: 5px 20px 0;
|
|
||||||
border: 1px solid $borderColor;
|
|
||||||
border-radius: 4px;
|
|
||||||
background-color: $white;
|
|
||||||
}
|
|
|
@ -1,107 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import sortByName from 'Utilities/Array/sortByName';
|
|
||||||
import { icons } from 'Helpers/Props';
|
|
||||||
import FieldSet from 'Components/FieldSet';
|
|
||||||
import Card from 'Components/Card';
|
|
||||||
import Icon from 'Components/Icon';
|
|
||||||
import PageSectionContent from 'Components/Page/PageSectionContent';
|
|
||||||
import LanguageProfile from './LanguageProfile';
|
|
||||||
import EditLanguageProfileModalConnector from './EditLanguageProfileModalConnector';
|
|
||||||
import styles from './LanguageProfiles.css';
|
|
||||||
|
|
||||||
class LanguageProfiles extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
constructor(props, context) {
|
|
||||||
super(props, context);
|
|
||||||
|
|
||||||
this.state = {
|
|
||||||
isLanguageProfileModalOpen: false
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onCloneLanguageProfilePress = (id) => {
|
|
||||||
this.props.onCloneLanguageProfilePress(id);
|
|
||||||
this.setState({ isLanguageProfileModalOpen: true });
|
|
||||||
}
|
|
||||||
|
|
||||||
onEditLanguageProfilePress = () => {
|
|
||||||
this.setState({ isLanguageProfileModalOpen: true });
|
|
||||||
}
|
|
||||||
|
|
||||||
onModalClose = () => {
|
|
||||||
this.setState({ isLanguageProfileModalOpen: false });
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
const {
|
|
||||||
items,
|
|
||||||
isDeleting,
|
|
||||||
onConfirmDeleteLanguageProfile,
|
|
||||||
...otherProps
|
|
||||||
} = this.props;
|
|
||||||
|
|
||||||
return (
|
|
||||||
<FieldSet legend="Language Profiles">
|
|
||||||
<PageSectionContent
|
|
||||||
errorMessage="Unable to load Language Profiles"
|
|
||||||
{...otherProps}
|
|
||||||
>
|
|
||||||
<div className={styles.languageProfiles}>
|
|
||||||
{
|
|
||||||
items.sort(sortByName).map((item) => {
|
|
||||||
return (
|
|
||||||
<LanguageProfile
|
|
||||||
key={item.id}
|
|
||||||
{...item}
|
|
||||||
isDeleting={isDeleting}
|
|
||||||
onConfirmDeleteLanguageProfile={onConfirmDeleteLanguageProfile}
|
|
||||||
onCloneLanguageProfilePress={this.onCloneLanguageProfilePress}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
<Card
|
|
||||||
className={styles.addLanguageProfile}
|
|
||||||
onPress={this.onEditLanguageProfilePress}
|
|
||||||
>
|
|
||||||
<div className={styles.center}>
|
|
||||||
<Icon
|
|
||||||
name={icons.ADD}
|
|
||||||
size={45}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</Card>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<EditLanguageProfileModalConnector
|
|
||||||
isOpen={this.state.isLanguageProfileModalOpen}
|
|
||||||
onModalClose={this.onModalClose}
|
|
||||||
/>
|
|
||||||
</PageSectionContent>
|
|
||||||
</FieldSet>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfiles.propTypes = {
|
|
||||||
advancedSettings: PropTypes.bool.isRequired,
|
|
||||||
isFetching: PropTypes.bool.isRequired,
|
|
||||||
error: PropTypes.object,
|
|
||||||
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
isDeleting: PropTypes.bool.isRequired,
|
|
||||||
onConfirmDeleteLanguageProfile: PropTypes.func.isRequired,
|
|
||||||
onCloneLanguageProfilePress: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default LanguageProfiles;
|
|
|
@ -1,67 +0,0 @@
|
||||||
import PropTypes from 'prop-types';
|
|
||||||
import React, { Component } from 'react';
|
|
||||||
import { connect } from 'react-redux';
|
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import { fetchLanguageProfiles, deleteLanguageProfile, cloneLanguageProfile } from 'Store/Actions/settingsActions';
|
|
||||||
import LanguageProfiles from './LanguageProfiles';
|
|
||||||
|
|
||||||
function createMapStateToProps() {
|
|
||||||
return createSelector(
|
|
||||||
(state) => state.settings.advancedSettings,
|
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(advancedSettings, languageProfiles) => {
|
|
||||||
return {
|
|
||||||
advancedSettings,
|
|
||||||
...languageProfiles
|
|
||||||
};
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
const mapDispatchToProps = {
|
|
||||||
dispatchFetchLanguageProfiles: fetchLanguageProfiles,
|
|
||||||
dispatchDeleteLanguageProfile: deleteLanguageProfile,
|
|
||||||
dispatchCloneLanguageProfile: cloneLanguageProfile
|
|
||||||
};
|
|
||||||
|
|
||||||
class LanguageProfilesConnector extends Component {
|
|
||||||
|
|
||||||
//
|
|
||||||
// Lifecycle
|
|
||||||
|
|
||||||
componentDidMount() {
|
|
||||||
this.props.dispatchFetchLanguageProfiles();
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Listeners
|
|
||||||
|
|
||||||
onConfirmDeleteLanguageProfile = (id) => {
|
|
||||||
this.props.dispatchDeleteLanguageProfile({ id });
|
|
||||||
}
|
|
||||||
|
|
||||||
onCloneLanguageProfilePress = (id) => {
|
|
||||||
this.props.dispatchCloneLanguageProfile({ id });
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// Render
|
|
||||||
|
|
||||||
render() {
|
|
||||||
return (
|
|
||||||
<LanguageProfiles
|
|
||||||
onConfirmDeleteLanguageProfile={this.onConfirmDeleteLanguageProfile}
|
|
||||||
onCloneLanguageProfilePress={this.onCloneLanguageProfilePress}
|
|
||||||
{...this.props}
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
LanguageProfilesConnector.propTypes = {
|
|
||||||
dispatchFetchLanguageProfiles: PropTypes.func.isRequired,
|
|
||||||
dispatchDeleteLanguageProfile: PropTypes.func.isRequired,
|
|
||||||
dispatchCloneLanguageProfile: PropTypes.func.isRequired
|
|
||||||
};
|
|
||||||
|
|
||||||
export default connect(createMapStateToProps, mapDispatchToProps)(LanguageProfilesConnector);
|
|
|
@ -5,7 +5,6 @@ import PageContent from 'Components/Page/PageContent';
|
||||||
import PageContentBodyConnector from 'Components/Page/PageContentBodyConnector';
|
import PageContentBodyConnector from 'Components/Page/PageContentBodyConnector';
|
||||||
import SettingsToolbarConnector from 'Settings/SettingsToolbarConnector';
|
import SettingsToolbarConnector from 'Settings/SettingsToolbarConnector';
|
||||||
import QualityProfilesConnector from './Quality/QualityProfilesConnector';
|
import QualityProfilesConnector from './Quality/QualityProfilesConnector';
|
||||||
import LanguageProfilesConnector from './Language/LanguageProfilesConnector';
|
|
||||||
import MetadataProfilesConnector from './Metadata/MetadataProfilesConnector';
|
import MetadataProfilesConnector from './Metadata/MetadataProfilesConnector';
|
||||||
import DelayProfilesConnector from './Delay/DelayProfilesConnector';
|
import DelayProfilesConnector from './Delay/DelayProfilesConnector';
|
||||||
import ReleaseProfilesConnector from './Release/ReleaseProfilesConnector';
|
import ReleaseProfilesConnector from './Release/ReleaseProfilesConnector';
|
||||||
|
@ -24,7 +23,6 @@ class Profiles extends Component {
|
||||||
|
|
||||||
<PageContentBodyConnector>
|
<PageContentBodyConnector>
|
||||||
<QualityProfilesConnector />
|
<QualityProfilesConnector />
|
||||||
<LanguageProfilesConnector />
|
|
||||||
<MetadataProfilesConnector />
|
<MetadataProfilesConnector />
|
||||||
<DelayProfilesConnector />
|
<DelayProfilesConnector />
|
||||||
<ReleaseProfilesConnector />
|
<ReleaseProfilesConnector />
|
||||||
|
|
|
@ -32,7 +32,7 @@ function Settings() {
|
||||||
</Link>
|
</Link>
|
||||||
|
|
||||||
<div className={styles.summary}>
|
<div className={styles.summary}>
|
||||||
Quality, Language, Metadata, Delay, and Release profiles
|
Quality, Metadata, Delay, and Release profiles
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<Link
|
<Link
|
||||||
|
|
|
@ -1,97 +0,0 @@
|
||||||
import { createAction } from 'redux-actions';
|
|
||||||
import { createThunk } from 'Store/thunks';
|
|
||||||
import getSectionState from 'Utilities/State/getSectionState';
|
|
||||||
import updateSectionState from 'Utilities/State/updateSectionState';
|
|
||||||
import createSetSettingValueReducer from 'Store/Actions/Creators/Reducers/createSetSettingValueReducer';
|
|
||||||
import createFetchHandler from 'Store/Actions/Creators/createFetchHandler';
|
|
||||||
import createFetchSchemaHandler from 'Store/Actions/Creators/createFetchSchemaHandler';
|
|
||||||
import createSaveProviderHandler from 'Store/Actions/Creators/createSaveProviderHandler';
|
|
||||||
import createRemoveItemHandler from 'Store/Actions/Creators/createRemoveItemHandler';
|
|
||||||
|
|
||||||
//
|
|
||||||
// Variables
|
|
||||||
|
|
||||||
const section = 'settings.languageProfiles';
|
|
||||||
|
|
||||||
//
|
|
||||||
// Actions Types
|
|
||||||
|
|
||||||
export const FETCH_LANGUAGE_PROFILES = 'settings/languageProfiles/fetchLanguageProfiles';
|
|
||||||
export const FETCH_LANGUAGE_PROFILE_SCHEMA = 'settings/languageProfiles/fetchLanguageProfileSchema';
|
|
||||||
export const SAVE_LANGUAGE_PROFILE = 'settings/languageProfiles/saveLanguageProfile';
|
|
||||||
export const DELETE_LANGUAGE_PROFILE = 'settings/languageProfiles/deleteLanguageProfile';
|
|
||||||
export const SET_LANGUAGE_PROFILE_VALUE = 'settings/languageProfiles/setLanguageProfileValue';
|
|
||||||
export const CLONE_LANGUAGE_PROFILE = 'settings/languageProfiles/cloneLanguageProfile';
|
|
||||||
|
|
||||||
//
|
|
||||||
// Action Creators
|
|
||||||
|
|
||||||
export const fetchLanguageProfiles = createThunk(FETCH_LANGUAGE_PROFILES);
|
|
||||||
export const fetchLanguageProfileSchema = createThunk(FETCH_LANGUAGE_PROFILE_SCHEMA);
|
|
||||||
export const saveLanguageProfile = createThunk(SAVE_LANGUAGE_PROFILE);
|
|
||||||
export const deleteLanguageProfile = createThunk(DELETE_LANGUAGE_PROFILE);
|
|
||||||
|
|
||||||
export const setLanguageProfileValue = createAction(SET_LANGUAGE_PROFILE_VALUE, (payload) => {
|
|
||||||
return {
|
|
||||||
section,
|
|
||||||
...payload
|
|
||||||
};
|
|
||||||
});
|
|
||||||
|
|
||||||
export const cloneLanguageProfile = createAction(CLONE_LANGUAGE_PROFILE);
|
|
||||||
|
|
||||||
//
|
|
||||||
// Details
|
|
||||||
|
|
||||||
export default {
|
|
||||||
|
|
||||||
//
|
|
||||||
// State
|
|
||||||
|
|
||||||
defaultState: {
|
|
||||||
isFetching: false,
|
|
||||||
isPopulated: false,
|
|
||||||
error: null,
|
|
||||||
isDeleting: false,
|
|
||||||
deleteError: null,
|
|
||||||
isSchemaFetching: false,
|
|
||||||
isSchemaPopulated: false,
|
|
||||||
schemaError: null,
|
|
||||||
schema: {},
|
|
||||||
isSaving: false,
|
|
||||||
saveError: null,
|
|
||||||
items: [],
|
|
||||||
pendingChanges: {}
|
|
||||||
},
|
|
||||||
|
|
||||||
//
|
|
||||||
// Action Handlers
|
|
||||||
|
|
||||||
actionHandlers: {
|
|
||||||
[FETCH_LANGUAGE_PROFILES]: createFetchHandler(section, '/languageprofile'),
|
|
||||||
[FETCH_LANGUAGE_PROFILE_SCHEMA]: createFetchSchemaHandler(section, '/languageprofile/schema'),
|
|
||||||
[SAVE_LANGUAGE_PROFILE]: createSaveProviderHandler(section, '/languageprofile'),
|
|
||||||
[DELETE_LANGUAGE_PROFILE]: createRemoveItemHandler(section, '/languageprofile')
|
|
||||||
},
|
|
||||||
|
|
||||||
//
|
|
||||||
// Reducers
|
|
||||||
|
|
||||||
reducers: {
|
|
||||||
[SET_LANGUAGE_PROFILE_VALUE]: createSetSettingValueReducer(section),
|
|
||||||
|
|
||||||
[CLONE_LANGUAGE_PROFILE]: function(state, { payload }) {
|
|
||||||
const id = payload.id;
|
|
||||||
const newState = getSectionState(state, section);
|
|
||||||
const item = newState.items.find((i) => i.id === id);
|
|
||||||
const pendingChanges = { ...item, id: 0 };
|
|
||||||
delete pendingChanges.id;
|
|
||||||
|
|
||||||
pendingChanges.name = `${pendingChanges.name} - Copy`;
|
|
||||||
newState.pendingChanges = pendingChanges;
|
|
||||||
|
|
||||||
return updateSectionState(state, section, newState);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
};
|
|
|
@ -14,8 +14,3 @@ export const SET_IS_SIDEBAR_VISIBLE = 'SET_IS_SIDEBAR_VISIBLE';
|
||||||
export const FETCH_GENERAL_SETTINGS = 'settings/general/fetchGeneralSettings';
|
export const FETCH_GENERAL_SETTINGS = 'settings/general/fetchGeneralSettings';
|
||||||
export const SET_GENERAL_SETTINGS_VALUE = 'settings/general/setGeneralSettingsValue';
|
export const SET_GENERAL_SETTINGS_VALUE = 'settings/general/setGeneralSettingsValue';
|
||||||
export const SAVE_GENERAL_SETTINGS = 'settings/general/saveGeneralSettings';
|
export const SAVE_GENERAL_SETTINGS = 'settings/general/saveGeneralSettings';
|
||||||
|
|
||||||
//
|
|
||||||
// Languages
|
|
||||||
|
|
||||||
export const FETCH_LANGUAGES = 'FETCH_LANGUAGES';
|
|
||||||
|
|
|
@ -33,7 +33,6 @@ export const defaultState = {
|
||||||
rootFolderPath: '',
|
rootFolderPath: '',
|
||||||
monitor: monitorOptions[0].key,
|
monitor: monitorOptions[0].key,
|
||||||
qualityProfileId: 0,
|
qualityProfileId: 0,
|
||||||
languageProfileId: 0,
|
|
||||||
metadataProfileId: 0,
|
metadataProfileId: 0,
|
||||||
albumFolder: true,
|
albumFolder: true,
|
||||||
tags: []
|
tags: []
|
||||||
|
|
|
@ -52,12 +52,6 @@ export const defaultState = {
|
||||||
type: filterBuilderTypes.EXACT,
|
type: filterBuilderTypes.EXACT,
|
||||||
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageProfileId',
|
|
||||||
label: 'Language Profile',
|
|
||||||
type: filterBuilderTypes.EXACT,
|
|
||||||
valueType: filterBuilderValueTypes.LANGUAGE_PROFILE
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'metadataProfileId',
|
name: 'metadataProfileId',
|
||||||
label: 'Metadata Profile',
|
label: 'Metadata Profile',
|
||||||
|
|
|
@ -49,12 +49,6 @@ export const defaultState = {
|
||||||
type: filterBuilderTypes.EXACT,
|
type: filterBuilderTypes.EXACT,
|
||||||
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageProfileId',
|
|
||||||
label: 'Language Profile',
|
|
||||||
type: filterBuilderTypes.EXACT,
|
|
||||||
valueType: filterBuilderValueTypes.LANGUAGE_PROFILE
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'metadataProfileId',
|
name: 'metadataProfileId',
|
||||||
label: 'Metadata Profile',
|
label: 'Metadata Profile',
|
||||||
|
|
|
@ -85,12 +85,6 @@ export const defaultState = {
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageProfileId',
|
|
||||||
label: 'Language Profile',
|
|
||||||
isSortable: true,
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'metadataProfileId',
|
name: 'metadataProfileId',
|
||||||
label: 'Metadata Profile',
|
label: 'Metadata Profile',
|
||||||
|
@ -250,12 +244,6 @@ export const defaultState = {
|
||||||
type: filterBuilderTypes.EXACT,
|
type: filterBuilderTypes.EXACT,
|
||||||
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
valueType: filterBuilderValueTypes.QUALITY_PROFILE
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'languageProfileId',
|
|
||||||
label: 'Language Profile',
|
|
||||||
type: filterBuilderTypes.EXACT,
|
|
||||||
valueType: filterBuilderValueTypes.LANGUAGE_PROFILE
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'metadataProfileId',
|
name: 'metadataProfileId',
|
||||||
label: 'Metadata Profile',
|
label: 'Metadata Profile',
|
||||||
|
|
|
@ -38,11 +38,6 @@ export const defaultState = {
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'quality',
|
name: 'quality',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
|
|
@ -50,11 +50,6 @@ export const defaultState = {
|
||||||
label: 'Track Title',
|
label: 'Track Title',
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'quality',
|
name: 'quality',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
|
|
@ -80,12 +80,6 @@ export const defaultState = {
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: false
|
isVisible: false
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isSortable: true,
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'quality',
|
name: 'quality',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
|
|
@ -7,7 +7,6 @@ import downloadClientOptions from './Settings/downloadClientOptions';
|
||||||
import general from './Settings/general';
|
import general from './Settings/general';
|
||||||
import indexerOptions from './Settings/indexerOptions';
|
import indexerOptions from './Settings/indexerOptions';
|
||||||
import indexers from './Settings/indexers';
|
import indexers from './Settings/indexers';
|
||||||
import languageProfiles from './Settings/languageProfiles';
|
|
||||||
import importLists from './Settings/importLists';
|
import importLists from './Settings/importLists';
|
||||||
import importListExclusions from './Settings/importListExclusions';
|
import importListExclusions from './Settings/importListExclusions';
|
||||||
import metadataProfiles from './Settings/metadataProfiles';
|
import metadataProfiles from './Settings/metadataProfiles';
|
||||||
|
@ -31,7 +30,6 @@ export * from './Settings/importLists';
|
||||||
export * from './Settings/importListExclusions';
|
export * from './Settings/importListExclusions';
|
||||||
export * from './Settings/indexerOptions';
|
export * from './Settings/indexerOptions';
|
||||||
export * from './Settings/indexers';
|
export * from './Settings/indexers';
|
||||||
export * from './Settings/languageProfiles';
|
|
||||||
export * from './Settings/metadataProfiles';
|
export * from './Settings/metadataProfiles';
|
||||||
export * from './Settings/mediaManagement';
|
export * from './Settings/mediaManagement';
|
||||||
export * from './Settings/metadata';
|
export * from './Settings/metadata';
|
||||||
|
@ -62,7 +60,6 @@ export const defaultState = {
|
||||||
general: general.defaultState,
|
general: general.defaultState,
|
||||||
indexerOptions: indexerOptions.defaultState,
|
indexerOptions: indexerOptions.defaultState,
|
||||||
indexers: indexers.defaultState,
|
indexers: indexers.defaultState,
|
||||||
languageProfiles: languageProfiles.defaultState,
|
|
||||||
importLists: importLists.defaultState,
|
importLists: importLists.defaultState,
|
||||||
importListExclusions: importListExclusions.defaultState,
|
importListExclusions: importListExclusions.defaultState,
|
||||||
metadataProfiles: metadataProfiles.defaultState,
|
metadataProfiles: metadataProfiles.defaultState,
|
||||||
|
@ -103,7 +100,6 @@ export const actionHandlers = handleThunks({
|
||||||
...general.actionHandlers,
|
...general.actionHandlers,
|
||||||
...indexerOptions.actionHandlers,
|
...indexerOptions.actionHandlers,
|
||||||
...indexers.actionHandlers,
|
...indexers.actionHandlers,
|
||||||
...languageProfiles.actionHandlers,
|
|
||||||
...importLists.actionHandlers,
|
...importLists.actionHandlers,
|
||||||
...importListExclusions.actionHandlers,
|
...importListExclusions.actionHandlers,
|
||||||
...metadataProfiles.actionHandlers,
|
...metadataProfiles.actionHandlers,
|
||||||
|
@ -135,7 +131,6 @@ export const reducers = createHandleActions({
|
||||||
...general.reducers,
|
...general.reducers,
|
||||||
...indexerOptions.reducers,
|
...indexerOptions.reducers,
|
||||||
...indexers.reducers,
|
...indexers.reducers,
|
||||||
...languageProfiles.reducers,
|
|
||||||
...importLists.reducers,
|
...importLists.reducers,
|
||||||
...importListExclusions.reducers,
|
...importListExclusions.reducers,
|
||||||
...metadataProfiles.reducers,
|
...metadataProfiles.reducers,
|
||||||
|
|
|
@ -55,11 +55,6 @@ export const defaultState = {
|
||||||
label: 'Duration',
|
label: 'Duration',
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'audioInfo',
|
name: 'audioInfo',
|
||||||
label: 'Audio Info',
|
label: 'Audio Info',
|
||||||
|
|
|
@ -139,7 +139,6 @@ export const actionHandlers = handleThunks({
|
||||||
[UPDATE_TRACK_FILES]: function(getState, payload, dispatch) {
|
[UPDATE_TRACK_FILES]: function(getState, payload, dispatch) {
|
||||||
const {
|
const {
|
||||||
trackFileIds,
|
trackFileIds,
|
||||||
language,
|
|
||||||
quality
|
quality
|
||||||
} = payload;
|
} = payload;
|
||||||
|
|
||||||
|
@ -149,10 +148,6 @@ export const actionHandlers = handleThunks({
|
||||||
trackFileIds
|
trackFileIds
|
||||||
};
|
};
|
||||||
|
|
||||||
if (language) {
|
|
||||||
data.language = language;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (quality) {
|
if (quality) {
|
||||||
data.quality = quality;
|
data.quality = quality;
|
||||||
}
|
}
|
||||||
|
@ -169,10 +164,6 @@ export const actionHandlers = handleThunks({
|
||||||
...trackFileIds.map((id) => {
|
...trackFileIds.map((id) => {
|
||||||
const props = {};
|
const props = {};
|
||||||
|
|
||||||
if (language) {
|
|
||||||
props.language = language;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (quality) {
|
if (quality) {
|
||||||
props.quality = quality;
|
props.quality = quality;
|
||||||
}
|
}
|
||||||
|
|
|
@ -125,11 +125,6 @@ export const defaultState = {
|
||||||
isSortable: true,
|
isSortable: true,
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: false
|
|
||||||
},
|
|
||||||
// {
|
// {
|
||||||
// name: 'status',
|
// name: 'status',
|
||||||
// label: 'Status',
|
// label: 'Status',
|
||||||
|
|
|
@ -1,16 +0,0 @@
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
import createArtistSelector from './createArtistSelector';
|
|
||||||
|
|
||||||
function createArtistLanguageProfileSelector() {
|
|
||||||
return createSelector(
|
|
||||||
(state) => state.settings.languageProfiles.items,
|
|
||||||
createArtistSelector(),
|
|
||||||
(languageProfiles, artist = {}) => {
|
|
||||||
return languageProfiles.find((profile) => {
|
|
||||||
return profile.id === artist.languageProfileId;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
export default createArtistLanguageProfileSelector;
|
|
|
@ -1,15 +0,0 @@
|
||||||
import { createSelector } from 'reselect';
|
|
||||||
|
|
||||||
function createLanguageProfileSelector() {
|
|
||||||
return createSelector(
|
|
||||||
(state, { languageProfileId }) => languageProfileId,
|
|
||||||
(state) => state.settings.languageProfiles.items,
|
|
||||||
(languageProfileId, languageProfiles) => {
|
|
||||||
return languageProfiles.find((profile) => {
|
|
||||||
return profile.id === languageProfileId;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
export default createLanguageProfileSelector;
|
|
|
@ -32,11 +32,6 @@ const columns = [
|
||||||
label: 'Relative Path',
|
label: 'Relative Path',
|
||||||
isVisible: true
|
isVisible: true
|
||||||
},
|
},
|
||||||
{
|
|
||||||
name: 'language',
|
|
||||||
label: 'Language',
|
|
||||||
isVisible: true
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
name: 'quality',
|
name: 'quality',
|
||||||
label: 'Quality',
|
label: 'Quality',
|
||||||
|
@ -112,16 +107,6 @@ class TrackFileEditorModalContent extends Component {
|
||||||
this.setState({ isConfirmDeleteModalOpen: false });
|
this.setState({ isConfirmDeleteModalOpen: false });
|
||||||
}
|
}
|
||||||
|
|
||||||
onLanguageChange = ({ value }) => {
|
|
||||||
const selectedIds = this.getSelectedIds();
|
|
||||||
|
|
||||||
if (!selectedIds.length) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.props.onLanguageChange(selectedIds, parseInt(value));
|
|
||||||
}
|
|
||||||
|
|
||||||
onQualityChange = ({ value }) => {
|
onQualityChange = ({ value }) => {
|
||||||
const selectedIds = this.getSelectedIds();
|
const selectedIds = this.getSelectedIds();
|
||||||
|
|
||||||
|
@ -142,7 +127,6 @@ class TrackFileEditorModalContent extends Component {
|
||||||
isPopulated,
|
isPopulated,
|
||||||
error,
|
error,
|
||||||
items,
|
items,
|
||||||
languages,
|
|
||||||
qualities,
|
qualities,
|
||||||
onModalClose
|
onModalClose
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
@ -154,15 +138,6 @@ class TrackFileEditorModalContent extends Component {
|
||||||
isConfirmDeleteModalOpen
|
isConfirmDeleteModalOpen
|
||||||
} = this.state;
|
} = this.state;
|
||||||
|
|
||||||
const languageOptions = _.reduceRight(languages, (acc, language) => {
|
|
||||||
acc.push({
|
|
||||||
key: language.id,
|
|
||||||
value: language.name
|
|
||||||
});
|
|
||||||
|
|
||||||
return acc;
|
|
||||||
}, [{ key: 'selectLanguage', value: 'Select Language', disabled: true }]);
|
|
||||||
|
|
||||||
const qualityOptions = _.reduceRight(qualities, (acc, quality) => {
|
const qualityOptions = _.reduceRight(qualities, (acc, quality) => {
|
||||||
acc.push({
|
acc.push({
|
||||||
key: quality.id,
|
key: quality.id,
|
||||||
|
@ -240,16 +215,6 @@ class TrackFileEditorModalContent extends Component {
|
||||||
Delete
|
Delete
|
||||||
</SpinnerButton>
|
</SpinnerButton>
|
||||||
|
|
||||||
<div className={styles.selectInput}>
|
|
||||||
<SelectInput
|
|
||||||
name="language"
|
|
||||||
value="selectLanguage"
|
|
||||||
values={languageOptions}
|
|
||||||
isDisabled={!hasSelectedFiles}
|
|
||||||
onChange={this.onLanguageChange}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div className={styles.selectInput}>
|
<div className={styles.selectInput}>
|
||||||
<SelectInput
|
<SelectInput
|
||||||
name="quality"
|
name="quality"
|
||||||
|
@ -288,10 +253,8 @@ TrackFileEditorModalContent.propTypes = {
|
||||||
isPopulated: PropTypes.bool.isRequired,
|
isPopulated: PropTypes.bool.isRequired,
|
||||||
error: PropTypes.object,
|
error: PropTypes.object,
|
||||||
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
items: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
languages: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
qualities: PropTypes.arrayOf(PropTypes.object).isRequired,
|
qualities: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
onDeletePress: PropTypes.func.isRequired,
|
onDeletePress: PropTypes.func.isRequired,
|
||||||
onLanguageChange: PropTypes.func.isRequired,
|
|
||||||
onQualityChange: PropTypes.func.isRequired,
|
onQualityChange: PropTypes.func.isRequired,
|
||||||
onModalClose: PropTypes.func.isRequired
|
onModalClose: PropTypes.func.isRequired
|
||||||
};
|
};
|
||||||
|
|
|
@ -8,30 +8,25 @@ import getQualities from 'Utilities/Quality/getQualities';
|
||||||
import createArtistSelector from 'Store/Selectors/createArtistSelector';
|
import createArtistSelector from 'Store/Selectors/createArtistSelector';
|
||||||
import { deleteTrackFiles, updateTrackFiles } from 'Store/Actions/trackFileActions';
|
import { deleteTrackFiles, updateTrackFiles } from 'Store/Actions/trackFileActions';
|
||||||
import { fetchTracks, clearTracks } from 'Store/Actions/trackActions';
|
import { fetchTracks, clearTracks } from 'Store/Actions/trackActions';
|
||||||
import { fetchLanguageProfileSchema, fetchQualityProfileSchema } from 'Store/Actions/settingsActions';
|
import { fetchQualityProfileSchema } from 'Store/Actions/settingsActions';
|
||||||
import TrackFileEditorModalContent from './TrackFileEditorModalContent';
|
import TrackFileEditorModalContent from './TrackFileEditorModalContent';
|
||||||
|
|
||||||
function createSchemaSelector() {
|
function createSchemaSelector() {
|
||||||
return createSelector(
|
return createSelector(
|
||||||
(state) => state.settings.languageProfiles,
|
|
||||||
(state) => state.settings.qualityProfiles,
|
(state) => state.settings.qualityProfiles,
|
||||||
(languageProfiles, qualityProfiles) => {
|
(qualityProfiles) => {
|
||||||
const languages = _.map(languageProfiles.schema.languages, 'language');
|
|
||||||
const qualities = getQualities(qualityProfiles.schema.items);
|
const qualities = getQualities(qualityProfiles.schema.items);
|
||||||
|
|
||||||
let error = null;
|
let error = null;
|
||||||
|
|
||||||
if (languageProfiles.schemaError) {
|
if (qualityProfiles.schemaError) {
|
||||||
error = 'Unable to load languages';
|
|
||||||
} else if (qualityProfiles.schemaError) {
|
|
||||||
error = 'Unable to load qualities';
|
error = 'Unable to load qualities';
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
isFetching: languageProfiles.isSchemaFetching || qualityProfiles.isSchemaFetching,
|
isFetching: qualityProfiles.isSchemaFetching,
|
||||||
isPopulated: languageProfiles.isSchemaPopulated && qualityProfiles.isSchemaPopulated,
|
isPopulated: qualityProfiles.isSchemaPopulated,
|
||||||
error,
|
error,
|
||||||
languages,
|
|
||||||
qualities
|
qualities
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -71,7 +66,6 @@ function createMapStateToProps() {
|
||||||
|
|
||||||
return {
|
return {
|
||||||
relativePath: trackFile.relativePath,
|
relativePath: trackFile.relativePath,
|
||||||
language: trackFile.language,
|
|
||||||
quality: trackFile.quality,
|
quality: trackFile.quality,
|
||||||
...track
|
...track
|
||||||
};
|
};
|
||||||
|
@ -98,10 +92,6 @@ function createMapDispatchToProps(dispatch, props) {
|
||||||
dispatch(fetchTracks(updateProps));
|
dispatch(fetchTracks(updateProps));
|
||||||
},
|
},
|
||||||
|
|
||||||
dispatchFetchLanguageProfileSchema(name, path) {
|
|
||||||
dispatch(fetchLanguageProfileSchema());
|
|
||||||
},
|
|
||||||
|
|
||||||
dispatchFetchQualityProfileSchema(name, path) {
|
dispatchFetchQualityProfileSchema(name, path) {
|
||||||
dispatch(fetchQualityProfileSchema());
|
dispatch(fetchQualityProfileSchema());
|
||||||
},
|
},
|
||||||
|
@ -127,7 +117,6 @@ class TrackFileEditorModalContentConnector extends Component {
|
||||||
|
|
||||||
this.props.dispatchFetchTracks({ artistId, albumId });
|
this.props.dispatchFetchTracks({ artistId, albumId });
|
||||||
|
|
||||||
this.props.dispatchFetchLanguageProfileSchema();
|
|
||||||
this.props.dispatchFetchQualityProfileSchema();
|
this.props.dispatchFetchQualityProfileSchema();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -138,12 +127,6 @@ class TrackFileEditorModalContentConnector extends Component {
|
||||||
//
|
//
|
||||||
// Listeners
|
// Listeners
|
||||||
|
|
||||||
onLanguageChange = (trackFileIds, languageId) => {
|
|
||||||
const language = _.find(this.props.languages, { id: languageId });
|
|
||||||
|
|
||||||
this.props.dispatchUpdateTrackFiles({ trackFileIds, language });
|
|
||||||
}
|
|
||||||
|
|
||||||
onQualityChange = (trackFileIds, qualityId) => {
|
onQualityChange = (trackFileIds, qualityId) => {
|
||||||
const quality = {
|
const quality = {
|
||||||
quality: _.find(this.props.qualities, { id: qualityId }),
|
quality: _.find(this.props.qualities, { id: qualityId }),
|
||||||
|
@ -161,7 +144,6 @@ class TrackFileEditorModalContentConnector extends Component {
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
const {
|
const {
|
||||||
dispatchFetchLanguageProfileSchema,
|
|
||||||
dispatchFetchQualityProfileSchema,
|
dispatchFetchQualityProfileSchema,
|
||||||
dispatchUpdateTrackFiles,
|
dispatchUpdateTrackFiles,
|
||||||
dispatchFetchTracks,
|
dispatchFetchTracks,
|
||||||
|
@ -172,7 +154,6 @@ class TrackFileEditorModalContentConnector extends Component {
|
||||||
return (
|
return (
|
||||||
<TrackFileEditorModalContent
|
<TrackFileEditorModalContent
|
||||||
{...otherProps}
|
{...otherProps}
|
||||||
onLanguageChange={this.onLanguageChange}
|
|
||||||
onQualityChange={this.onQualityChange}
|
onQualityChange={this.onQualityChange}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
@ -182,11 +163,9 @@ class TrackFileEditorModalContentConnector extends Component {
|
||||||
TrackFileEditorModalContentConnector.propTypes = {
|
TrackFileEditorModalContentConnector.propTypes = {
|
||||||
artistId: PropTypes.number.isRequired,
|
artistId: PropTypes.number.isRequired,
|
||||||
albumId: PropTypes.number,
|
albumId: PropTypes.number,
|
||||||
languages: PropTypes.arrayOf(PropTypes.object).isRequired,
|
|
||||||
qualities: PropTypes.arrayOf(PropTypes.object).isRequired,
|
qualities: PropTypes.arrayOf(PropTypes.object).isRequired,
|
||||||
dispatchFetchTracks: PropTypes.func.isRequired,
|
dispatchFetchTracks: PropTypes.func.isRequired,
|
||||||
dispatchClearTracks: PropTypes.func.isRequired,
|
dispatchClearTracks: PropTypes.func.isRequired,
|
||||||
dispatchFetchLanguageProfileSchema: PropTypes.func.isRequired,
|
|
||||||
dispatchFetchQualityProfileSchema: PropTypes.func.isRequired,
|
dispatchFetchQualityProfileSchema: PropTypes.func.isRequired,
|
||||||
dispatchUpdateTrackFiles: PropTypes.func.isRequired
|
dispatchUpdateTrackFiles: PropTypes.func.isRequired
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,7 +1,6 @@
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import padNumber from 'Utilities/Number/padNumber';
|
import padNumber from 'Utilities/Number/padNumber';
|
||||||
import Label from 'Components/Label';
|
|
||||||
import TableRow from 'Components/Table/TableRow';
|
import TableRow from 'Components/Table/TableRow';
|
||||||
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
import TableRowCell from 'Components/Table/Cells/TableRowCell';
|
||||||
import TableSelectCell from 'Components/Table/Cells/TableSelectCell';
|
import TableSelectCell from 'Components/Table/Cells/TableSelectCell';
|
||||||
|
@ -12,7 +11,6 @@ function TrackFileEditorRow(props) {
|
||||||
id,
|
id,
|
||||||
trackNumber,
|
trackNumber,
|
||||||
relativePath,
|
relativePath,
|
||||||
language,
|
|
||||||
quality,
|
quality,
|
||||||
isSelected,
|
isSelected,
|
||||||
onSelectedChange
|
onSelectedChange
|
||||||
|
@ -34,12 +32,6 @@ function TrackFileEditorRow(props) {
|
||||||
{relativePath}
|
{relativePath}
|
||||||
</TableRowCell>
|
</TableRowCell>
|
||||||
|
|
||||||
<TableRowCell>
|
|
||||||
<Label>
|
|
||||||
{language.name}
|
|
||||||
</Label>
|
|
||||||
</TableRowCell>
|
|
||||||
|
|
||||||
<TableRowCell>
|
<TableRowCell>
|
||||||
<TrackQuality
|
<TrackQuality
|
||||||
quality={quality}
|
quality={quality}
|
||||||
|
@ -53,7 +45,6 @@ TrackFileEditorRow.propTypes = {
|
||||||
id: PropTypes.number.isRequired,
|
id: PropTypes.number.isRequired,
|
||||||
trackNumber: PropTypes.string.isRequired,
|
trackNumber: PropTypes.string.isRequired,
|
||||||
relativePath: PropTypes.string.isRequired,
|
relativePath: PropTypes.string.isRequired,
|
||||||
language: PropTypes.object.isRequired,
|
|
||||||
quality: PropTypes.object.isRequired,
|
quality: PropTypes.object.isRequired,
|
||||||
isSelected: PropTypes.bool,
|
isSelected: PropTypes.bool,
|
||||||
onSelectedChange: PropTypes.func.isRequired
|
onSelectedChange: PropTypes.func.isRequired
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue