mirror of
https://github.com/Sonarr/Sonarr.git
synced 2024-12-14 11:23:42 +02:00
New: Alternate styling for progress bars when color impaired mode is enabled
This commit is contained in:
parent
647e444a07
commit
ef7a08879f
@ -209,7 +209,6 @@
|
|||||||
"lines-around-comment": ["error", { "beforeBlockComment": true, "afterBlockComment": false }],
|
"lines-around-comment": ["error", { "beforeBlockComment": true, "afterBlockComment": false }],
|
||||||
"max-depth": ["error", {"maximum": 5}],
|
"max-depth": ["error", {"maximum": 5}],
|
||||||
"max-nested-callbacks": ["error", 4],
|
"max-nested-callbacks": ["error", 4],
|
||||||
"max-params": ["error", 6],
|
|
||||||
"max-statements": "off",
|
"max-statements": "off",
|
||||||
"max-statements-per-line": ["error", { "max": 1 }],
|
"max-statements-per-line": ["error", { "max": 1 }],
|
||||||
"new-cap": ["error", {"capIsNewExceptions": ["$.Deferred", "DragDropContext", "DragLayer", "DragSource", "DropTarget"]}],
|
"new-cap": ["error", {"capIsNewExceptions": ["$.Deferred", "DragDropContext", "DragLayer", "DragSource", "DropTarget"]}],
|
||||||
|
6
frontend/src/App/ColorImpairedContext.js
Normal file
6
frontend/src/App/ColorImpairedContext.js
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
import React from 'react';
|
||||||
|
|
||||||
|
const ColorImpairedContext = React.createContext(false);
|
||||||
|
export const ColorImpairedConsumer = ColorImpairedContext.Consumer;
|
||||||
|
|
||||||
|
export default ColorImpairedContext;
|
@ -63,6 +63,21 @@ function Legend(props) {
|
|||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div>
|
||||||
|
<LegendItem
|
||||||
|
status="onAir"
|
||||||
|
name="On Air"
|
||||||
|
tooltip="Episode is currently airing"
|
||||||
|
colorImpairedMode={colorImpairedMode}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<LegendItem
|
||||||
|
status="missing"
|
||||||
|
tooltip="Episode has aired and is missing from disk"
|
||||||
|
colorImpairedMode={colorImpairedMode}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
<LegendItem
|
<LegendItem
|
||||||
status="downloading"
|
status="downloading"
|
||||||
|
@ -2,8 +2,9 @@ import PropTypes from 'prop-types';
|
|||||||
import React, { Component } from 'react';
|
import React, { Component } from 'react';
|
||||||
import locationShape from 'Helpers/Props/Shapes/locationShape';
|
import locationShape from 'Helpers/Props/Shapes/locationShape';
|
||||||
import SignalRConnector from 'Components/SignalRConnector';
|
import SignalRConnector from 'Components/SignalRConnector';
|
||||||
import AppUpdatedModalConnector from 'App/AppUpdatedModalConnector';
|
import ColorImpairedContext from 'App/ColorImpairedContext';
|
||||||
import ConnectionLostModalConnector from 'App/ConnectionLostModalConnector';
|
import ConnectionLostModalConnector from 'App/ConnectionLostModalConnector';
|
||||||
|
import AppUpdatedModalConnector from 'App/AppUpdatedModalConnector';
|
||||||
import PageHeader from './Header/PageHeader';
|
import PageHeader from './Header/PageHeader';
|
||||||
import PageSidebar from './Sidebar/PageSidebar';
|
import PageSidebar from './Sidebar/PageSidebar';
|
||||||
import styles from './Page.css';
|
import styles from './Page.css';
|
||||||
@ -73,11 +74,13 @@ class Page extends Component {
|
|||||||
children,
|
children,
|
||||||
isSmallScreen,
|
isSmallScreen,
|
||||||
isSidebarVisible,
|
isSidebarVisible,
|
||||||
|
enableColorImpairedMode,
|
||||||
onSidebarToggle,
|
onSidebarToggle,
|
||||||
onSidebarVisibleChange
|
onSidebarVisibleChange
|
||||||
} = this.props;
|
} = this.props;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
<ColorImpairedContext.Provider value={enableColorImpairedMode}>
|
||||||
<div className={className}>
|
<div className={className}>
|
||||||
<SignalRConnector />
|
<SignalRConnector />
|
||||||
|
|
||||||
@ -106,6 +109,7 @@ class Page extends Component {
|
|||||||
onModalClose={this.onConnectionLostModalClose}
|
onModalClose={this.onConnectionLostModalClose}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
|
</ColorImpairedContext.Provider>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -118,6 +122,7 @@ Page.propTypes = {
|
|||||||
isSidebarVisible: PropTypes.bool.isRequired,
|
isSidebarVisible: PropTypes.bool.isRequired,
|
||||||
isUpdated: PropTypes.bool.isRequired,
|
isUpdated: PropTypes.bool.isRequired,
|
||||||
isDisconnected: PropTypes.bool.isRequired,
|
isDisconnected: PropTypes.bool.isRequired,
|
||||||
|
enableColorImpairedMode: PropTypes.bool.isRequired,
|
||||||
onResize: PropTypes.func.isRequired,
|
onResize: PropTypes.func.isRequired,
|
||||||
onSidebarToggle: PropTypes.func.isRequired,
|
onSidebarToggle: PropTypes.func.isRequired,
|
||||||
onSidebarVisibleChange: PropTypes.func.isRequired
|
onSidebarVisibleChange: PropTypes.func.isRequired
|
||||||
|
@ -32,25 +32,37 @@ function createMapStateToProps() {
|
|||||||
(state) => state.series,
|
(state) => state.series,
|
||||||
(state) => state.customFilters,
|
(state) => state.customFilters,
|
||||||
(state) => state.tags,
|
(state) => state.tags,
|
||||||
(state) => state.settings,
|
(state) => state.settings.ui,
|
||||||
|
(state) => state.settings.qualityProfiles,
|
||||||
|
(state) => state.settings.languageProfiles,
|
||||||
(state) => state.app,
|
(state) => state.app,
|
||||||
createDimensionsSelector(),
|
createDimensionsSelector(),
|
||||||
(series, customFilters, tags, settings, app, dimensions) => {
|
(
|
||||||
|
series,
|
||||||
|
customFilters,
|
||||||
|
tags,
|
||||||
|
uiSettings,
|
||||||
|
qualityProfiles,
|
||||||
|
languageProfiles,
|
||||||
|
app,
|
||||||
|
dimensions
|
||||||
|
) => {
|
||||||
const isPopulated = (
|
const isPopulated = (
|
||||||
series.isPopulated &&
|
series.isPopulated &&
|
||||||
customFilters.isPopulated &&
|
customFilters.isPopulated &&
|
||||||
tags.isPopulated &&
|
tags.isPopulated &&
|
||||||
settings.qualityProfiles.isPopulated &&
|
qualityProfiles.isPopulated &&
|
||||||
settings.ui.isPopulated
|
languageProfiles.isPopulated &&
|
||||||
|
uiSettings.isPopulated
|
||||||
);
|
);
|
||||||
|
|
||||||
const hasError = !!(
|
const hasError = !!(
|
||||||
series.error ||
|
series.error ||
|
||||||
customFilters.error ||
|
customFilters.error ||
|
||||||
tags.error ||
|
tags.error ||
|
||||||
settings.qualityProfiles.error ||
|
qualityProfiles.error ||
|
||||||
settings.languageProfiles.error ||
|
languageProfiles.error ||
|
||||||
settings.ui.error
|
uiSettings.error
|
||||||
);
|
);
|
||||||
|
|
||||||
return {
|
return {
|
||||||
@ -59,10 +71,12 @@ function createMapStateToProps() {
|
|||||||
seriesError: series.error,
|
seriesError: series.error,
|
||||||
customFiltersError: tags.error,
|
customFiltersError: tags.error,
|
||||||
tagsError: tags.error,
|
tagsError: tags.error,
|
||||||
qualityProfilesError: settings.qualityProfiles.error,
|
qualityProfilesError: qualityProfiles.error,
|
||||||
uiSettingsError: settings.ui.error,
|
languageProfilesError: languageProfiles.error,
|
||||||
|
uiSettingsError: uiSettings.error,
|
||||||
isSmallScreen: dimensions.isSmallScreen,
|
isSmallScreen: dimensions.isSmallScreen,
|
||||||
isSidebarVisible: app.isSidebarVisible,
|
isSidebarVisible: app.isSidebarVisible,
|
||||||
|
enableColorImpairedMode: uiSettings.item.enableColorImpairedMode,
|
||||||
version: app.version,
|
version: app.version,
|
||||||
isUpdated: app.isUpdated,
|
isUpdated: app.isUpdated,
|
||||||
isDisconnected: app.isDisconnected
|
isDisconnected: app.isDisconnected
|
||||||
|
@ -43,10 +43,18 @@
|
|||||||
|
|
||||||
.primary {
|
.primary {
|
||||||
background-color: $primaryColor;
|
background-color: $primaryColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $primaryColor, $primaryColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.danger {
|
.danger {
|
||||||
background-color: $dangerColor;
|
background-color: $dangerColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $dangerColor, $dangerColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.success {
|
.success {
|
||||||
@ -59,6 +67,10 @@
|
|||||||
|
|
||||||
.warning {
|
.warning {
|
||||||
background-color: $warningColor;
|
background-color: $warningColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $warningColor, $warningColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.info {
|
.info {
|
||||||
|
@ -2,6 +2,7 @@ import PropTypes from 'prop-types';
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import classNames from 'classnames';
|
import classNames from 'classnames';
|
||||||
import { kinds, sizes } from 'Helpers/Props';
|
import { kinds, sizes } from 'Helpers/Props';
|
||||||
|
import { ColorImpairedConsumer } from 'App/ColorImpairedContext';
|
||||||
import styles from './ProgressBar.css';
|
import styles from './ProgressBar.css';
|
||||||
|
|
||||||
function ProgressBar(props) {
|
function ProgressBar(props) {
|
||||||
@ -22,6 +23,9 @@ function ProgressBar(props) {
|
|||||||
const progressText = text || progressPercent;
|
const progressText = text || progressPercent;
|
||||||
const actualWidth = width ? `${width}px` : '100%';
|
const actualWidth = width ? `${width}px` : '100%';
|
||||||
|
|
||||||
|
return (
|
||||||
|
<ColorImpairedConsumer>
|
||||||
|
{(enableColorImpairedMode) => {
|
||||||
return (
|
return (
|
||||||
<div
|
<div
|
||||||
className={classNames(
|
className={classNames(
|
||||||
@ -32,7 +36,7 @@ function ProgressBar(props) {
|
|||||||
style={{ width: actualWidth }}
|
style={{ width: actualWidth }}
|
||||||
>
|
>
|
||||||
{
|
{
|
||||||
showText && !!width &&
|
showText && width ?
|
||||||
<div
|
<div
|
||||||
className={styles.backTextContainer}
|
className={styles.backTextContainer}
|
||||||
style={{ width: actualWidth }}
|
style={{ width: actualWidth }}
|
||||||
@ -42,21 +46,24 @@ function ProgressBar(props) {
|
|||||||
{progressText}
|
{progressText}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div> :
|
||||||
|
null
|
||||||
}
|
}
|
||||||
|
|
||||||
<div
|
<div
|
||||||
className={classNames(
|
className={classNames(
|
||||||
className,
|
className,
|
||||||
styles[kind]
|
styles[kind],
|
||||||
|
enableColorImpairedMode && 'colorImpaired'
|
||||||
)}
|
)}
|
||||||
aria-valuenow={progress}
|
aria-valuenow={progress}
|
||||||
aria-valuemin="0"
|
aria-valuemin="0"
|
||||||
aria-valuemax="100"
|
aria-valuemax="100"
|
||||||
style={{ width: progressPercent }}
|
style={{ width: progressPercent }}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{
|
{
|
||||||
showText &&
|
showText ?
|
||||||
<div
|
<div
|
||||||
className={styles.frontTextContainer}
|
className={styles.frontTextContainer}
|
||||||
style={{ width: progressPercent }}
|
style={{ width: progressPercent }}
|
||||||
@ -69,10 +76,14 @@ function ProgressBar(props) {
|
|||||||
{progressText}
|
{progressText}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div> :
|
||||||
|
null
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
}}
|
||||||
|
</ColorImpairedConsumer>
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
ProgressBar.propTypes = {
|
ProgressBar.propTypes = {
|
||||||
|
@ -22,6 +22,10 @@
|
|||||||
composes: legendItemColor;
|
composes: legendItemColor;
|
||||||
|
|
||||||
background-color: $primaryColor;
|
background-color: $primaryColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $primaryColor, $primaryColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.ended {
|
.ended {
|
||||||
@ -34,12 +38,20 @@
|
|||||||
composes: legendItemColor;
|
composes: legendItemColor;
|
||||||
|
|
||||||
background-color: $dangerColor;
|
background-color: $dangerColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $dangerColor, $dangerColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.missingUnmonitored {
|
.missingUnmonitored {
|
||||||
composes: legendItemColor;
|
composes: legendItemColor;
|
||||||
|
|
||||||
background-color: $warningColor;
|
background-color: $warningColor;
|
||||||
|
|
||||||
|
&:global(.colorImpaired) {
|
||||||
|
background: repeating-linear-gradient(90deg, $warningColor, $warningColor 10px, $colorImpairedAlternateGradient 10px, $colorImpairedAlternateGradient 20px);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.statistics {
|
.statistics {
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
|
import classNames from 'classnames';
|
||||||
import formatBytes from 'Utilities/Number/formatBytes';
|
import formatBytes from 'Utilities/Number/formatBytes';
|
||||||
|
import { ColorImpairedConsumer } from 'App/ColorImpairedContext';
|
||||||
import DescriptionList from 'Components/DescriptionList/DescriptionList';
|
import DescriptionList from 'Components/DescriptionList/DescriptionList';
|
||||||
import DescriptionListItem from 'Components/DescriptionList/DescriptionListItem';
|
import DescriptionListItem from 'Components/DescriptionList/DescriptionListItem';
|
||||||
import styles from './SeriesIndexFooter.css';
|
import styles from './SeriesIndexFooter.css';
|
||||||
@ -39,26 +41,49 @@ function SeriesIndexFooter({ series }) {
|
|||||||
totalFileSize += sizeOnDisk;
|
totalFileSize += sizeOnDisk;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
return (
|
||||||
|
<ColorImpairedConsumer>
|
||||||
|
{(enableColorImpairedMode) => {
|
||||||
return (
|
return (
|
||||||
<div className={styles.footer}>
|
<div className={styles.footer}>
|
||||||
<div>
|
<div>
|
||||||
<div className={styles.legendItem}>
|
<div className={styles.legendItem}>
|
||||||
<div className={styles.continuing} />
|
<div
|
||||||
|
className={classNames(
|
||||||
|
styles.continuing,
|
||||||
|
enableColorImpairedMode && 'colorImpaired'
|
||||||
|
)}
|
||||||
|
/>
|
||||||
<div>Continuing (All episodes downloaded)</div>
|
<div>Continuing (All episodes downloaded)</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className={styles.legendItem}>
|
<div className={styles.legendItem}>
|
||||||
<div className={styles.ended} />
|
<div
|
||||||
|
className={classNames(
|
||||||
|
styles.ended,
|
||||||
|
enableColorImpairedMode && 'colorImpaired'
|
||||||
|
)}
|
||||||
|
/>
|
||||||
<div>Ended (All episodes downloaded)</div>
|
<div>Ended (All episodes downloaded)</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className={styles.legendItem}>
|
<div className={styles.legendItem}>
|
||||||
<div className={styles.missingMonitored} />
|
<div
|
||||||
|
className={classNames(
|
||||||
|
styles.missingMonitored,
|
||||||
|
enableColorImpairedMode && 'colorImpaired'
|
||||||
|
)}
|
||||||
|
/>
|
||||||
<div>Missing Episodes (Series monitored)</div>
|
<div>Missing Episodes (Series monitored)</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div className={styles.legendItem}>
|
<div className={styles.legendItem}>
|
||||||
<div className={styles.missingUnmonitored} />
|
<div
|
||||||
|
className={classNames(
|
||||||
|
styles.missingUnmonitored,
|
||||||
|
enableColorImpairedMode && 'colorImpaired'
|
||||||
|
)}
|
||||||
|
/>
|
||||||
<div>Missing Episodes (Series not monitored)</div>
|
<div>Missing Episodes (Series not monitored)</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@ -114,6 +139,9 @@ function SeriesIndexFooter({ series }) {
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
}}
|
||||||
|
</ColorImpairedConsumer>
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
SeriesIndexFooter.propTypes = {
|
SeriesIndexFooter.propTypes = {
|
||||||
|
@ -62,6 +62,7 @@ module.exports = {
|
|||||||
inputWarningBorderColor: '#ffa500',
|
inputWarningBorderColor: '#ffa500',
|
||||||
inputWarningBoxShadowColor: 'rgba(255, 165, 0, 0.6)',
|
inputWarningBoxShadowColor: 'rgba(255, 165, 0, 0.6)',
|
||||||
colorImpairedGradient: '#fcfcfc',
|
colorImpairedGradient: '#fcfcfc',
|
||||||
|
colorImpairedAlternateGradient: '#b0b0b0',
|
||||||
|
|
||||||
//
|
//
|
||||||
// Buttons
|
// Buttons
|
||||||
|
Loading…
Reference in New Issue
Block a user