mirror of https://github.com/mue/mue.git
refactor: settings tabs, improvements to logic + readability
Co-authored-by: David Ralph <me@davidcralph.co.uk>
This commit is contained in:
parent
85b0e9826c
commit
bd9c868196
|
@ -1,7 +1,7 @@
|
|||
{
|
||||
"compilerOptions": {
|
||||
"module": "commonjs",
|
||||
"target": "es6",
|
||||
"target": "es6"
|
||||
},
|
||||
"exclude": ["node_modules"],
|
||||
"exclude": ["node_modules"]
|
||||
}
|
||||
|
|
|
@ -20,7 +20,7 @@
|
|||
"@muetab/react-color-gradient-picker": "0.1.2",
|
||||
"@muetab/react-sortable-hoc": "^2.0.1",
|
||||
"@mui/material": "5.15.7",
|
||||
"@sentry/react": "^7.100.0",
|
||||
"@sentry/react": "^7.100.1",
|
||||
"embla-carousel-autoplay": "8.0.0-rc22",
|
||||
"embla-carousel-react": "8.0.0-rc22",
|
||||
"fast-blurhash": "^1.1.2",
|
||||
|
|
713
pnpm-lock.yaml
713
pnpm-lock.yaml
File diff suppressed because it is too large
Load Diff
|
@ -10,8 +10,6 @@ import EventBus from 'modules/helpers/eventbus';
|
|||
|
||||
import Welcome from './welcome/Welcome';
|
||||
|
||||
import Apps from './apps/Apps';
|
||||
|
||||
export default class Modals extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
|
@ -78,9 +76,6 @@ export default class Modals extends PureComponent {
|
|||
}
|
||||
|
||||
render() {
|
||||
const navZoom = localStorage.getItem('zoomNavbar');
|
||||
const appsInfo = JSON.parse(localStorage.getItem('applinks'));
|
||||
|
||||
return (
|
||||
<>
|
||||
{this.state.welcomeModal === false && (
|
||||
|
@ -108,27 +103,6 @@ export default class Modals extends PureComponent {
|
|||
>
|
||||
<Welcome modalClose={() => this.closeWelcome()} modalSkip={() => this.previewWelcome()} />
|
||||
</Modal>
|
||||
|
||||
<Modal
|
||||
closeTimeoutMS={300}
|
||||
onRequestClose={() => this.toggleModal('appsModal', false)}
|
||||
isOpen={this.state.appsModal}
|
||||
className="Modal appsmodal"
|
||||
overlayClassName="Overlay"
|
||||
shouldCloseOnOverlayClick={true}
|
||||
ariaHideApp={false}
|
||||
style={{
|
||||
content: {
|
||||
position: 'absolute',
|
||||
right: '1rem',
|
||||
top: `calc(1rem + ${55 + Math.ceil((navZoom / 20) * (navZoom * 0.01))}px)`,
|
||||
overflow: 'visible',
|
||||
},
|
||||
}}
|
||||
>
|
||||
<Apps appsInfo={appsInfo} />
|
||||
</Modal>
|
||||
|
||||
{this.state.preview && <Preview setup={() => window.location.reload()} />}
|
||||
</>
|
||||
);
|
||||
|
|
|
@ -1,47 +0,0 @@
|
|||
import variables from 'modules/variables';
|
||||
import { MdLinkOff } from 'react-icons/md';
|
||||
|
||||
import Tooltip from 'components/helpers/tooltip/Tooltip';
|
||||
|
||||
import './scss/index.scss';
|
||||
|
||||
const Apps = ({ appsInfo }) => {
|
||||
return (
|
||||
<div className="appsShortcutContainer">
|
||||
{appsInfo.length > 0 ? (
|
||||
appsInfo.map((info, i) => (
|
||||
<Tooltip
|
||||
title={info.name.split(' ')[0]}
|
||||
subtitle={info.name.split(' ').slice(1).join(' ')}
|
||||
key={i}
|
||||
>
|
||||
<a href={info.url} className="appsIcon">
|
||||
<img
|
||||
src={
|
||||
info.icon === ''
|
||||
? `https://icon.horse/icon/ ${info.url.replace('https://', '').replace('http://', '')}`
|
||||
: info.icon
|
||||
}
|
||||
width="40px"
|
||||
height="40px"
|
||||
alt="Google"
|
||||
/>
|
||||
<span>{info.name}</span>
|
||||
</a>
|
||||
</Tooltip>
|
||||
))
|
||||
) : (
|
||||
<div className="noAppsContainer">
|
||||
<div className="emptyNewMessage">
|
||||
<MdLinkOff />
|
||||
<span className="title">
|
||||
{variables.language.getMessage(variables.languagecode, 'widgets.navbar.apps.no_apps')}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export default Apps;
|
|
@ -114,7 +114,7 @@ class Marketplace extends PureComponent {
|
|||
).json();
|
||||
this.setState({
|
||||
items: collection.data.items,
|
||||
collectionTitle: collection.data.name,
|
||||
collectionTitle: collection.data.display_name,
|
||||
collectionDescription: collection.data.description,
|
||||
collectionImg: collection.data.img,
|
||||
collection: true,
|
||||
|
@ -235,14 +235,6 @@ class Marketplace extends PureComponent {
|
|||
});
|
||||
}
|
||||
|
||||
reloadItems() {
|
||||
this.setState({
|
||||
done: false,
|
||||
});
|
||||
|
||||
this.getItems();
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (navigator.onLine === false || localStorage.getItem('offlineMode') === 'true') {
|
||||
return;
|
||||
|
@ -344,7 +336,7 @@ class Marketplace extends PureComponent {
|
|||
<div
|
||||
className="collectionPage"
|
||||
style={{
|
||||
backgroundImage: `linear-gradient(to bottom, transparent, black), url('${this.state.collectionImg}')`,
|
||||
backgroundImage: `linear-gradient(to bottom, transparent, black), url('${variables.constants.DDG_IMAGE_PROXY + this.state.collectionImg}')`,
|
||||
}}
|
||||
>
|
||||
<div className="nice-tag">
|
||||
|
@ -386,9 +378,6 @@ class Marketplace extends PureComponent {
|
|||
/>
|
||||
<MdSearch />
|
||||
</form>
|
||||
{/*<span className="link marketplaceRefresh" onClick={() => this.reloadItems()}>
|
||||
<MdRefresh /> {variables.getMessage('widgets.navbar.tooltips.refresh')}
|
||||
</span>*/}
|
||||
</div>
|
||||
)}
|
||||
<Dropdown
|
||||
|
@ -412,7 +401,7 @@ class Marketplace extends PureComponent {
|
|||
item.news
|
||||
? { backgroundColor: item.background_colour }
|
||||
: {
|
||||
backgroundImage: `linear-gradient(to left, #000, transparent, #000), url('${item.img}')`,
|
||||
backgroundImage: `linear-gradient(to left, #000, transparent, #000), url('${variables.constants.DDG_IMAGE_PROXY + item.img}')`,
|
||||
}
|
||||
}
|
||||
>
|
||||
|
|
|
@ -51,6 +51,7 @@ div.color-preview-area > div > div:nth-child(5) {
|
|||
justify-content: space-between;
|
||||
align-items: center;
|
||||
flex-flow: row-reverse;
|
||||
gap: 20px;
|
||||
}
|
||||
|
||||
.gradient-controls {
|
||||
|
|
|
@ -16,7 +16,7 @@ const PreferencesWrapper = ({ children, ...props }) => {
|
|||
});
|
||||
|
||||
return (
|
||||
<div className={shown ? '' : 'inactiveSetting'}>
|
||||
<div className={shown ? 'preferences' : 'preferencesInactive'}>
|
||||
{props.zoomSetting && (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(
|
||||
|
|
|
@ -0,0 +1,18 @@
|
|||
import { MdOutlineKeyboardArrowRight } from 'react-icons/md';
|
||||
|
||||
export default function Section({ title, subtitle, icon, onClick }) {
|
||||
return (
|
||||
<div className="moreSettings" onClick={onClick}>
|
||||
<div className="left">
|
||||
{icon}
|
||||
<div className="content">
|
||||
<span className="title">{title}</span>
|
||||
<span className="subtitle">{subtitle}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="action">
|
||||
<MdOutlineKeyboardArrowRight />
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
}
|
|
@ -6,6 +6,8 @@ import {
|
|||
MdUpload as ImportIcon,
|
||||
MdDownload as ExportIcon,
|
||||
MdRestartAlt as ResetIcon,
|
||||
MdOutlineKeyboardArrowRight,
|
||||
MdDataUsage,
|
||||
} from 'react-icons/md';
|
||||
|
||||
import { exportSettings, importSettings } from 'modules/helpers/settings/modals';
|
||||
|
@ -16,106 +18,153 @@ import Switch from '../Switch';
|
|||
import ResetModal from '../ResetModal';
|
||||
import Dropdown from '../Dropdown';
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import Section from '../Section';
|
||||
|
||||
import time_zones from 'components/widgets/time/timezones.json';
|
||||
|
||||
export default function AdvancedSettings() {
|
||||
const [resetModal, setResetModal] = useState(false);
|
||||
const [data, setData] = useState(false);
|
||||
const ADVANCED_SECTION = 'modals.main.settings.sections.advanced';
|
||||
|
||||
const Data = () => {
|
||||
return (
|
||||
<>
|
||||
{localStorage.getItem('welcomePreview') !== 'true' && (
|
||||
<div className="settingsRow">
|
||||
<div className="content">
|
||||
<span className="title">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.data')}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.data_subtitle')}
|
||||
</span>
|
||||
</div>
|
||||
<div className="action activityButtons">
|
||||
<button onClick={() => setResetModal(true)}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
<ResetIcon />
|
||||
</button>
|
||||
<button onClick={() => exportSettings()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.export')}
|
||||
<ExportIcon />
|
||||
</button>
|
||||
<button onClick={() => document.getElementById('file-input').click()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.import')}
|
||||
<ImportIcon />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
let header;
|
||||
if (data) {
|
||||
header = (
|
||||
<span className="mainTitle">
|
||||
<span className="backTitle" onClick={() => setData(false)}>
|
||||
{variables.getMessage(`${ADVANCED_SECTION}.title`)}
|
||||
</span>
|
||||
<MdOutlineKeyboardArrowRight />
|
||||
{variables.getMessage(`${ADVANCED_SECTION}.data`)}
|
||||
</span>
|
||||
);
|
||||
} else {
|
||||
header = (
|
||||
<span className="mainTitle"> {variables.getMessage(`${ADVANCED_SECTION}.title`)}</span>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<span className="mainTitle">{variables.getMessage(`${ADVANCED_SECTION}.title`)}</span>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.offline_mode')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.advanced.offline_subtitle')}
|
||||
>
|
||||
<Switch name="offlineMode" element=".other" />
|
||||
</SettingsItem>
|
||||
{localStorage.getItem('welcomePreview') !== 'true' && (
|
||||
<div className="settingsRow">
|
||||
<div className="content">
|
||||
<span className="title">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.data')}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.data_subtitle')}
|
||||
</span>
|
||||
</div>
|
||||
<div className="action activityButtons">
|
||||
<button onClick={() => setResetModal(true)}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
<ResetIcon />
|
||||
</button>
|
||||
<button onClick={() => exportSettings()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.export')}
|
||||
<ExportIcon />
|
||||
</button>
|
||||
<button onClick={() => document.getElementById('file-input').click()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.import')}
|
||||
<ImportIcon />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
{header}
|
||||
{data ? (
|
||||
<Data />
|
||||
) : (
|
||||
<>
|
||||
<Section
|
||||
title={variables.getMessage(`${ADVANCED_SECTION}.data`)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.accessibility.description',
|
||||
)}
|
||||
onClick={() => setData(true)}
|
||||
icon={<MdDataUsage />}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.offline_mode')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.offline_subtitle',
|
||||
)}
|
||||
>
|
||||
<Switch name="offlineMode" element=".other" />
|
||||
</SettingsItem>
|
||||
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.timezone.title')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.timezone.subtitle',
|
||||
)}
|
||||
>
|
||||
<Dropdown name="timezone" category="timezone" manual={true}>
|
||||
<MenuItem value="auto">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.timezone.automatic')}
|
||||
</MenuItem>
|
||||
{time_zones.map((timezone) => (
|
||||
<MenuItem value={timezone} key={timezone}>
|
||||
{timezone}
|
||||
</MenuItem>
|
||||
))}
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.tab_name')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.tab_name_subtitle',
|
||||
)}
|
||||
>
|
||||
<Text name="tabName" default={variables.getMessage('tabname')} category="other" />
|
||||
</SettingsItem>
|
||||
<FileUpload
|
||||
id="file-input"
|
||||
accept="application/json"
|
||||
type="settings"
|
||||
loadFunction={(e) => importSettings(e)}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.custom_css')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.custom_css_subtitle',
|
||||
)}
|
||||
>
|
||||
<Text name="customcss" textarea={true} category="other" customcss={true} />
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.experimental.title')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.experimental_warning',
|
||||
)}
|
||||
final={true}
|
||||
>
|
||||
<Switch
|
||||
name="experimental"
|
||||
text={variables.getMessage('modals.main.settings.enabled')}
|
||||
element=".other"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<Modal
|
||||
closeTimeoutMS={100}
|
||||
onRequestClose={() => setResetModal(false)}
|
||||
isOpen={resetModal}
|
||||
className="Modal resetmodal mainModal"
|
||||
overlayClassName="Overlay resetoverlay"
|
||||
ariaHideApp={false}
|
||||
>
|
||||
<ResetModal modalClose={() => setResetModal(false)} />
|
||||
</Modal>
|
||||
</>
|
||||
)}
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.timezone.title')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.advanced.timezone.subtitle')}
|
||||
>
|
||||
<Dropdown name="timezone" category="timezone" manual={true}>
|
||||
<MenuItem value="auto">
|
||||
{variables.getMessage('modals.main.settings.sections.advanced.timezone.automatic')}
|
||||
</MenuItem>
|
||||
{time_zones.map((timezone) => (
|
||||
<MenuItem value={timezone} key={timezone}>
|
||||
{timezone}
|
||||
</MenuItem>
|
||||
))}
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.tab_name')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.advanced.tab_name_subtitle')}
|
||||
>
|
||||
<Text name="tabName" default={variables.getMessage('tabname')} category="other" />
|
||||
</SettingsItem>
|
||||
<FileUpload
|
||||
id="file-input"
|
||||
accept="application/json"
|
||||
type="settings"
|
||||
loadFunction={(e) => importSettings(e)}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.advanced.custom_css')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.custom_css_subtitle',
|
||||
)}
|
||||
>
|
||||
<Text name="customcss" textarea={true} category="other" customcss={true} />
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.experimental.title')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.advanced.experimental_warning',
|
||||
)}
|
||||
final={true}
|
||||
>
|
||||
<Switch
|
||||
name="experimental"
|
||||
text={variables.getMessage('modals.main.settings.enabled')}
|
||||
element=".other"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<Modal
|
||||
closeTimeoutMS={100}
|
||||
onRequestClose={() => setResetModal(false)}
|
||||
isOpen={resetModal}
|
||||
className="Modal resetmodal mainModal"
|
||||
overlayClassName="Overlay resetoverlay"
|
||||
ariaHideApp={false}
|
||||
>
|
||||
<ResetModal modalClose={() => setResetModal(false)} />
|
||||
</Modal>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { memo } from 'react';
|
||||
import { memo, useState } from 'react';
|
||||
|
||||
import variables from 'modules/variables';
|
||||
|
||||
|
@ -8,125 +8,119 @@ import Radio from '../Radio';
|
|||
import Slider from '../Slider';
|
||||
import Text from '../Text';
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import Section from '../Section';
|
||||
|
||||
import { MdSource, MdOutlineKeyboardArrowRight, MdAccessibility } from 'react-icons/md';
|
||||
|
||||
import { values } from 'modules/helpers/settings/modals';
|
||||
import Settings from '../../tabs/Settings';
|
||||
|
||||
function AppearanceSettings() {
|
||||
return (
|
||||
<>
|
||||
<span className="mainTitle">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.title')}
|
||||
</span>
|
||||
<div className="settingsRow">
|
||||
<div className="content">
|
||||
<span className="title">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.theme.title')}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{' '}
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.theme.description')}
|
||||
</span>
|
||||
</div>
|
||||
<div className="action">
|
||||
<Radio
|
||||
name="theme"
|
||||
options={[
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.auto'),
|
||||
value: 'auto',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.light'),
|
||||
value: 'light',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.dark'),
|
||||
value: 'dark',
|
||||
},
|
||||
]}
|
||||
category="other"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div className="settingsRow">
|
||||
<div className="content">
|
||||
<span className="title">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.title')}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.description')}
|
||||
</span>
|
||||
</div>
|
||||
<div className="action">
|
||||
<Checkbox
|
||||
name="fontGoogle"
|
||||
text={variables.getMessage('modals.main.settings.sections.appearance.font.google')}
|
||||
category="other"
|
||||
/>
|
||||
<Text
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.font.custom')}
|
||||
name="font"
|
||||
upperCaseFirst={true}
|
||||
category="other"
|
||||
/>
|
||||
<Dropdown
|
||||
label={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.title',
|
||||
const [accessibility, setAccessibility] = useState(false);
|
||||
|
||||
const ThemeSelection = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.theme.title')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.theme.description',
|
||||
)}
|
||||
>
|
||||
<Radio
|
||||
name="theme"
|
||||
options={[
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.auto'),
|
||||
value: 'auto',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.light'),
|
||||
value: 'light',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage('modals.main.settings.sections.appearance.theme.dark'),
|
||||
value: 'dark',
|
||||
},
|
||||
]}
|
||||
category="other"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const FontOptions = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.font.title')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.appearance.font.description')}
|
||||
>
|
||||
<Checkbox
|
||||
name="fontGoogle"
|
||||
text={variables.getMessage('modals.main.settings.sections.appearance.font.google')}
|
||||
category="other"
|
||||
/>
|
||||
<Text
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.font.custom')}
|
||||
name="font"
|
||||
upperCaseFirst={true}
|
||||
category="other"
|
||||
/>
|
||||
<Dropdown
|
||||
label={variables.getMessage('modals.main.settings.sections.appearance.font.weight.title')}
|
||||
name="fontweight"
|
||||
category="other"
|
||||
>
|
||||
{/* names are taken from https://developer.mozilla.org/en-US/docs/Web/CSS/font-weight */}
|
||||
<option value="100">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.thin')}
|
||||
</option>
|
||||
<option value="200">
|
||||
{variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.extra_light',
|
||||
)}
|
||||
name="fontweight"
|
||||
category="other"
|
||||
>
|
||||
{/* names are taken from https://developer.mozilla.org/en-US/docs/Web/CSS/font-weight */}
|
||||
<option value="100">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.thin')}
|
||||
</option>
|
||||
<option value="200">
|
||||
{variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.extra_light',
|
||||
)}
|
||||
</option>
|
||||
<option value="300">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.light')}
|
||||
</option>
|
||||
<option value="400">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.normal')}
|
||||
</option>
|
||||
<option value="500">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.medium')}
|
||||
</option>
|
||||
<option value="600">
|
||||
{variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.semi_bold',
|
||||
)}
|
||||
</option>
|
||||
<option value="700">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.bold')}
|
||||
</option>
|
||||
<option value="800">
|
||||
{variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.extra_bold',
|
||||
)}
|
||||
</option>
|
||||
</Dropdown>
|
||||
<Dropdown
|
||||
label={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.style.title',
|
||||
</option>
|
||||
<option value="300">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.light')}
|
||||
</option>
|
||||
<option value="400">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.normal')}
|
||||
</option>
|
||||
<option value="500">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.medium')}
|
||||
</option>
|
||||
<option value="600">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.semi_bold')}
|
||||
</option>
|
||||
<option value="700">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.weight.bold')}
|
||||
</option>
|
||||
<option value="800">
|
||||
{variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.font.weight.extra_bold',
|
||||
)}
|
||||
name="fontstyle"
|
||||
category="other"
|
||||
>
|
||||
<option value="normal">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.normal')}
|
||||
</option>
|
||||
<option value="italic">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.italic')}
|
||||
</option>
|
||||
<option value="oblique">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.oblique')}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</div>
|
||||
</div>
|
||||
</option>
|
||||
</Dropdown>
|
||||
<Dropdown
|
||||
label={variables.getMessage('modals.main.settings.sections.appearance.font.style.title')}
|
||||
name="fontstyle"
|
||||
category="other"
|
||||
>
|
||||
<option value="normal">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.normal')}
|
||||
</option>
|
||||
<option value="italic">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.italic')}
|
||||
</option>
|
||||
<option value="oblique">
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.font.style.oblique')}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const WidgetStyle = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.style.title')}
|
||||
subtitle={variables.getMessage(
|
||||
|
@ -149,7 +143,11 @@ function AppearanceSettings() {
|
|||
category="widgets"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const AccessibilityOptions = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.appearance.accessibility.title')}
|
||||
subtitle={variables.getMessage(
|
||||
|
@ -207,6 +205,50 @@ function AppearanceSettings() {
|
|||
}
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
let header;
|
||||
if (accessibility) {
|
||||
header = (
|
||||
<span className="mainTitle">
|
||||
<span className="backTitle" onClick={() => setAccessibility(false)}>
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.title')}
|
||||
</span>
|
||||
<MdOutlineKeyboardArrowRight />
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.accessibility.title')}
|
||||
</span>
|
||||
);
|
||||
} else {
|
||||
header = (
|
||||
<span className="mainTitle">
|
||||
{' '}
|
||||
{variables.getMessage('modals.main.settings.sections.appearance.title')}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
return (
|
||||
<>
|
||||
{header}
|
||||
{accessibility ? (
|
||||
<AccessibilityOptions />
|
||||
) : (
|
||||
<>
|
||||
<Section
|
||||
title={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.accessibility.title',
|
||||
)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.appearance.accessibility.description',
|
||||
)}
|
||||
icon={<MdAccessibility />}
|
||||
onClick={() => setAccessibility(true)}
|
||||
/>
|
||||
<ThemeSelection />
|
||||
<FontOptions />
|
||||
<WidgetStyle />
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -5,6 +5,7 @@ import Header from '../Header';
|
|||
import Checkbox from '../Checkbox';
|
||||
import Dropdown from '../Dropdown';
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default function Date() {
|
||||
const [dateType, setDateType] = useState(localStorage.getItem('dateType') || 'long');
|
||||
|
@ -75,47 +76,49 @@ export default function Date() {
|
|||
zoomSetting="zoomDate"
|
||||
switch={true}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.time.type')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.date.type.subtitle')}
|
||||
>
|
||||
<Dropdown
|
||||
name="dateType"
|
||||
onChange={(value) => {
|
||||
setDateType(value);
|
||||
localStorage.setItem('dateType', value);
|
||||
}}
|
||||
category="date"
|
||||
<PreferencesWrapper setting="date" switch={true} zoomSetting="zoomDate">
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.sections.time.type')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.date.type.subtitle')}
|
||||
>
|
||||
<option value="long">
|
||||
{variables.getMessage('modals.main.settings.sections.date.type.long')}
|
||||
</option>
|
||||
<option value="short">
|
||||
{variables.getMessage('modals.main.settings.sections.date.type.short')}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={
|
||||
dateType === 'long'
|
||||
? variables.getMessage('modals.main.settings.sections.date.type.long')
|
||||
: variables.getMessage('modals.main.settings.sections.date.type.short')
|
||||
}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.date.type_settings')}
|
||||
final={true}
|
||||
>
|
||||
{dateType === 'long' ? longSettings : shortSettings}
|
||||
<Checkbox
|
||||
name="weeknumber"
|
||||
text={variables.getMessage('modals.main.settings.sections.date.week_number')}
|
||||
category="date"
|
||||
/>
|
||||
<Checkbox
|
||||
name="datezero"
|
||||
text={variables.getMessage('modals.main.settings.sections.time.digital.zero')}
|
||||
category="date"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<Dropdown
|
||||
name="dateType"
|
||||
onChange={(value) => {
|
||||
setDateType(value);
|
||||
localStorage.setItem('dateType', value);
|
||||
}}
|
||||
category="date"
|
||||
>
|
||||
<option value="long">
|
||||
{variables.getMessage('modals.main.settings.sections.date.type.long')}
|
||||
</option>
|
||||
<option value="short">
|
||||
{variables.getMessage('modals.main.settings.sections.date.type.short')}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={
|
||||
dateType === 'long'
|
||||
? variables.getMessage('modals.main.settings.sections.date.type.long')
|
||||
: variables.getMessage('modals.main.settings.sections.date.type.short')
|
||||
}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.date.type_settings')}
|
||||
final={true}
|
||||
>
|
||||
{dateType === 'long' ? longSettings : shortSettings}
|
||||
<Checkbox
|
||||
name="weeknumber"
|
||||
text={variables.getMessage('modals.main.settings.sections.date.week_number')}
|
||||
category="date"
|
||||
/>
|
||||
<Checkbox
|
||||
name="datezero"
|
||||
text={variables.getMessage('modals.main.settings.sections.time.digital.zero')}
|
||||
category="date"
|
||||
/>
|
||||
</SettingsItem>
|
||||
</PreferencesWrapper>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,89 +1,97 @@
|
|||
import variables from 'modules/variables';
|
||||
import { PureComponent } from 'react';
|
||||
import { useState } from 'react';
|
||||
|
||||
import Header from '../Header';
|
||||
import Checkbox from '../Checkbox';
|
||||
import Switch from '../Switch';
|
||||
import Text from '../Text';
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class GreetingSettings extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
birthday: new Date(localStorage.getItem('birthday')) || new Date(),
|
||||
};
|
||||
}
|
||||
const GreetingSettings = () => {
|
||||
const [birthday, setBirthday] = useState(
|
||||
new Date(localStorage.getItem('birthday')) || new Date(),
|
||||
);
|
||||
|
||||
changeDate = (e) => {
|
||||
localStorage.setItem('birthday', e.target.value || new Date());
|
||||
|
||||
this.setState({
|
||||
birthday: e.target.value ? new Date(e.target.value) : new Date(),
|
||||
});
|
||||
const changeDate = (e) => {
|
||||
const newDate = e.target.value ? new Date(e.target.value) : new Date();
|
||||
localStorage.setItem('birthday', newDate);
|
||||
setBirthday(newDate);
|
||||
};
|
||||
|
||||
render() {
|
||||
const GREETING_SECTION = 'modals.main.settings.sections.greeting';
|
||||
const GREETING_SECTION = 'modals.main.settings.sections.greeting';
|
||||
|
||||
const AdditionalOptions = () => {
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${GREETING_SECTION}.title`)}
|
||||
setting="greeting"
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.additional_settings')}
|
||||
subtitle={variables.getMessage(`${GREETING_SECTION}.additional`)}
|
||||
>
|
||||
<Checkbox
|
||||
name="events"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.events`)}
|
||||
category="greeting"
|
||||
element=".greeting"
|
||||
zoomSetting="zoomGreeting"
|
||||
switch={true}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.additional_settings')}
|
||||
subtitle={variables.getMessage(`${GREETING_SECTION}.additional`)}
|
||||
>
|
||||
<Checkbox
|
||||
name="events"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.events`)}
|
||||
category="greeting"
|
||||
/>
|
||||
<Checkbox
|
||||
name="defaultGreetingMessage"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.default`)}
|
||||
category="greeting"
|
||||
/>
|
||||
<Text
|
||||
title={variables.getMessage(`${GREETING_SECTION}.name`)}
|
||||
name="greetingName"
|
||||
category="greeting"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${GREETING_SECTION}.birthday`)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.greeting.birthday_subtitle',
|
||||
)}
|
||||
final={true}
|
||||
>
|
||||
<Switch
|
||||
name="birthdayenabled"
|
||||
text={variables.getMessage('modals.main.settings.enabled')}
|
||||
category="greeting"
|
||||
/>
|
||||
<Checkbox
|
||||
name="birthdayage"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.birthday_age`)}
|
||||
category="greeting"
|
||||
/>
|
||||
<p style={{ marginRight: 'auto' }}>
|
||||
{variables.getMessage(`${GREETING_SECTION}.birthday_date`)}
|
||||
</p>
|
||||
<input
|
||||
type="date"
|
||||
onChange={this.changeDate}
|
||||
value={this.state.birthday.toISOString().substring(0, 10)}
|
||||
required
|
||||
/>
|
||||
</SettingsItem>
|
||||
</>
|
||||
<Checkbox
|
||||
name="defaultGreetingMessage"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.default`)}
|
||||
category="greeting"
|
||||
/>
|
||||
<Text
|
||||
title={variables.getMessage(`${GREETING_SECTION}.name`)}
|
||||
name="greetingName"
|
||||
category="greeting"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
const BirthdayOptions = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${GREETING_SECTION}.birthday`)}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.greeting.birthday_subtitle')}
|
||||
final={true}
|
||||
>
|
||||
<Switch
|
||||
name="birthdayenabled"
|
||||
text={variables.getMessage('modals.main.settings.enabled')}
|
||||
category="greeting"
|
||||
/>
|
||||
<Checkbox
|
||||
name="birthdayage"
|
||||
text={variables.getMessage(`${GREETING_SECTION}.birthday_age`)}
|
||||
category="greeting"
|
||||
/>
|
||||
<p style={{ marginRight: 'auto' }}>
|
||||
{variables.getMessage(`${GREETING_SECTION}.birthday_date`)}
|
||||
</p>
|
||||
<input
|
||||
type="date"
|
||||
onChange={changeDate}
|
||||
value={birthday.toISOString().substring(0, 10)}
|
||||
required
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${GREETING_SECTION}.title`)}
|
||||
setting="greeting"
|
||||
category="greeting"
|
||||
element=".greeting"
|
||||
zoomSetting="zoomGreeting"
|
||||
switch={true}
|
||||
/>
|
||||
<PreferencesWrapper setting="greeting" zoomSetting="zoomGreeting" switch={true}>
|
||||
<AdditionalOptions />
|
||||
{BirthdayOptions()}
|
||||
</PreferencesWrapper>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
export default GreetingSettings;
|
||||
|
|
|
@ -8,6 +8,7 @@ import SettingsItem from '../SettingsItem';
|
|||
import Header from '../Header';
|
||||
|
||||
import EventBus from 'modules/helpers/eventbus';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class Message extends PureComponent {
|
||||
constructor() {
|
||||
|
@ -70,64 +71,66 @@ export default class Message extends PureComponent {
|
|||
zoomSetting="zoomMessage"
|
||||
switch={true}
|
||||
/>
|
||||
<SettingsItem title={variables.getMessage(`${MESSAGE_SECTION}.messages`)} final={true}>
|
||||
<button onClick={() => this.modifyMessage('add')}>
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add`)} <MdAdd />
|
||||
</button>
|
||||
</SettingsItem>
|
||||
<div className="messagesContainer">
|
||||
{this.state.messages.map((_url, index) => (
|
||||
<div className="messageMap" key={index}>
|
||||
<div className="flexGrow">
|
||||
<div className="icon">
|
||||
<MdOutlineTextsms />
|
||||
<PreferencesWrapper setting="message" switch={true} zoomSetting="zoomMessage">
|
||||
<SettingsItem title={variables.getMessage(`${MESSAGE_SECTION}.messages`)} final={true}>
|
||||
<button onClick={() => this.modifyMessage('add')}>
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add`)} <MdAdd />
|
||||
</button>
|
||||
</SettingsItem>
|
||||
<div className="messagesContainer">
|
||||
{this.state.messages.map((_url, index) => (
|
||||
<div className="messageMap" key={index}>
|
||||
<div className="flexGrow">
|
||||
<div className="icon">
|
||||
<MdOutlineTextsms />
|
||||
</div>
|
||||
<div className="messageText">
|
||||
<span className="subtitle">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.title`)}
|
||||
</span>
|
||||
<TextareaAutosize
|
||||
value={this.state.messages[index]}
|
||||
placeholder={variables.getMessage(
|
||||
'modals.main.settings.sections.message.content',
|
||||
)}
|
||||
onChange={(e) => this.message(e, true, index)}
|
||||
varient="outlined"
|
||||
style={{ padding: '0' }}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
<div className="messageText">
|
||||
<span className="subtitle">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.title`)}
|
||||
</span>
|
||||
<TextareaAutosize
|
||||
value={this.state.messages[index]}
|
||||
placeholder={variables.getMessage(
|
||||
'modals.main.settings.sections.message.content',
|
||||
)}
|
||||
onChange={(e) => this.message(e, true, index)}
|
||||
varient="outlined"
|
||||
style={{ padding: '0' }}
|
||||
/>
|
||||
<div>
|
||||
<div className="messageAction">
|
||||
<button
|
||||
className="deleteButton"
|
||||
onClick={() => this.modifyMessage('remove', index)}
|
||||
>
|
||||
{variables.getMessage('modals.main.marketplace.product.buttons.remove')}
|
||||
<MdCancel />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div className="messageAction">
|
||||
<button
|
||||
className="deleteButton"
|
||||
onClick={() => this.modifyMessage('remove', index)}
|
||||
>
|
||||
{variables.getMessage('modals.main.marketplace.product.buttons.remove')}
|
||||
<MdCancel />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
{this.state.messages.length === 0 && (
|
||||
<div className="photosEmpty">
|
||||
<div className="emptyNewMessage">
|
||||
<MdOutlineTextsms />
|
||||
<span className="title">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.no_messages`)}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add_some`)}
|
||||
</span>
|
||||
<button onClick={() => this.modifyMessage('add')}>
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add`)}
|
||||
<MdAdd />
|
||||
</button>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
)}
|
||||
{this.state.messages.length === 0 && (
|
||||
<div className="photosEmpty">
|
||||
<div className="emptyNewMessage">
|
||||
<MdOutlineTextsms />
|
||||
<span className="title">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.no_messages`)}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add_some`)}
|
||||
</span>
|
||||
<button onClick={() => this.modifyMessage('add')}>
|
||||
{variables.getMessage(`${MESSAGE_SECTION}.add`)}
|
||||
<MdAdd />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</PreferencesWrapper>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -12,7 +12,7 @@ import Dropdown from '../Dropdown';
|
|||
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import Header from '../Header';
|
||||
import { getTitleFromUrl, isValidUrl } from './utils/utils';
|
||||
import { getTitleFromUrl, isValidUrl } from 'modules/helpers/settings/modals';
|
||||
import QuickLink from './quicklinks/QuickLink';
|
||||
|
||||
function Navbar() {
|
||||
|
@ -32,7 +32,7 @@ function Navbar() {
|
|||
const data = JSON.parse(localStorage.getItem('applinks'));
|
||||
|
||||
if (!url.startsWith('http://') && !url.startsWith('https://')) {
|
||||
url = 'http://' + url;
|
||||
url = 'https://' + url;
|
||||
}
|
||||
|
||||
if (url.length <= 0 || isValidUrl(url) === false) {
|
||||
|
|
|
@ -11,7 +11,8 @@ import AddModal from './quicklinks/AddModal';
|
|||
|
||||
import EventBus from 'modules/helpers/eventbus';
|
||||
import QuickLink from './quicklinks/QuickLink';
|
||||
import { getTitleFromUrl, isValidUrl } from './utils/utils';
|
||||
import { getTitleFromUrl, isValidUrl } from 'modules/helpers/settings/modals';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class QuickLinks extends PureComponent {
|
||||
constructor() {
|
||||
|
@ -136,67 +137,69 @@ export default class QuickLinks extends PureComponent {
|
|||
zoomSetting="zoomQuicklinks"
|
||||
switch={true}
|
||||
/>
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.additional_settings')}
|
||||
subtitle={variables.getMessage(`${QUICKLINKS_SECTION}.additional`)}
|
||||
>
|
||||
<Checkbox
|
||||
name="quicklinksnewtab"
|
||||
text={variables.getMessage(`${QUICKLINKS_SECTION}.open_new`)}
|
||||
category="quicklinks"
|
||||
/>
|
||||
<Checkbox
|
||||
name="quicklinkstooltip"
|
||||
text={variables.getMessage(`${QUICKLINKS_SECTION}.tooltip`)}
|
||||
category="quicklinks"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${QUICKLINKS_SECTION}.styling`)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.quicklinks.styling_description',
|
||||
)}
|
||||
>
|
||||
<Dropdown
|
||||
label={variables.getMessage(`${QUICKLINKS_SECTION}.style`)}
|
||||
name="quickLinksStyle"
|
||||
category="quicklinks"
|
||||
<PreferencesWrapper setting="quicklinksenabled" switch={true} zoomSetting="zoomQuicklinks">
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.additional_settings')}
|
||||
subtitle={variables.getMessage(`${QUICKLINKS_SECTION}.additional`)}
|
||||
>
|
||||
<option value="icon">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.icon`)}
|
||||
</option>
|
||||
<option value="text">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.text_only`)}
|
||||
</option>
|
||||
<option value="metro">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.metro`)}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<Checkbox
|
||||
name="quicklinksnewtab"
|
||||
text={variables.getMessage(`${QUICKLINKS_SECTION}.open_new`)}
|
||||
category="quicklinks"
|
||||
/>
|
||||
<Checkbox
|
||||
name="quicklinkstooltip"
|
||||
text={variables.getMessage(`${QUICKLINKS_SECTION}.tooltip`)}
|
||||
category="quicklinks"
|
||||
/>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${QUICKLINKS_SECTION}.styling`)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.quicklinks.styling_description',
|
||||
)}
|
||||
>
|
||||
<Dropdown
|
||||
label={variables.getMessage(`${QUICKLINKS_SECTION}.style`)}
|
||||
name="quickLinksStyle"
|
||||
category="quicklinks"
|
||||
>
|
||||
<option value="icon">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.icon`)}
|
||||
</option>
|
||||
<option value="text">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.text_only`)}
|
||||
</option>
|
||||
<option value="metro">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.options.metro`)}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
|
||||
<SettingsItem title={variables.getMessage(`${QUICKLINKS_SECTION}.title`)} final={true}>
|
||||
<button onClick={() => this.setState({ showAddModal: true })}>
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.add_link`)} <MdAddLink />
|
||||
</button>
|
||||
</SettingsItem>
|
||||
<SettingsItem title={variables.getMessage(`${QUICKLINKS_SECTION}.title`)} final={true}>
|
||||
<button onClick={() => this.setState({ showAddModal: true })}>
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.add_link`)} <MdAddLink />
|
||||
</button>
|
||||
</SettingsItem>
|
||||
|
||||
{this.state.items.length === 0 && (
|
||||
<div className="photosEmpty">
|
||||
<div className="emptyNewMessage">
|
||||
<MdLinkOff />
|
||||
<span className="title">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.no_quicklinks`)}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage('modals.main.settings.sections.message.add_some')}
|
||||
</span>
|
||||
<button onClick={() => this.setState({ showAddModal: true })}>
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.add_link`)}
|
||||
<MdAddLink />
|
||||
</button>
|
||||
{this.state.items.length === 0 && (
|
||||
<div className="photosEmpty">
|
||||
<div className="emptyNewMessage">
|
||||
<MdLinkOff />
|
||||
<span className="title">
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.no_quicklinks`)}
|
||||
</span>
|
||||
<span className="subtitle">
|
||||
{variables.getMessage('modals.main.settings.sections.message.add_some')}
|
||||
</span>
|
||||
<button onClick={() => this.setState({ showAddModal: true })}>
|
||||
{variables.getMessage(`${QUICKLINKS_SECTION}.add_link`)}
|
||||
<MdAddLink />
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
)}
|
||||
</PreferencesWrapper>
|
||||
|
||||
<div className="messagesContainer" ref={this.quicklinksContainer}>
|
||||
{this.state.items.map((item, i) => (
|
||||
|
|
|
@ -11,13 +11,13 @@ import SettingsItem from '../SettingsItem';
|
|||
import EventBus from 'modules/helpers/eventbus';
|
||||
|
||||
import searchEngines from 'components/widgets/search/search_engines.json';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class SearchSettings extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
customEnabled: false,
|
||||
customDisplay: 'none',
|
||||
customValue: localStorage.getItem('customSearchEngine') || '',
|
||||
};
|
||||
}
|
||||
|
@ -34,7 +34,6 @@ export default class SearchSettings extends PureComponent {
|
|||
componentDidMount() {
|
||||
if (localStorage.getItem('searchEngine') === 'custom') {
|
||||
this.setState({
|
||||
customDisplay: 'block',
|
||||
customEnabled: true,
|
||||
});
|
||||
} else {
|
||||
|
@ -53,12 +52,10 @@ export default class SearchSettings extends PureComponent {
|
|||
setSearchEngine(input) {
|
||||
if (input === 'custom') {
|
||||
this.setState({
|
||||
customDisplay: 'block',
|
||||
customEnabled: true,
|
||||
});
|
||||
} else {
|
||||
this.setState({
|
||||
customDisplay: 'none',
|
||||
customEnabled: false,
|
||||
});
|
||||
localStorage.setItem('searchEngine', input);
|
||||
|
@ -70,14 +67,8 @@ export default class SearchSettings extends PureComponent {
|
|||
render() {
|
||||
const SEARCH_SECTION = 'modals.main.settings.sections.search';
|
||||
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${SEARCH_SECTION}.title`)}
|
||||
setting="searchBar"
|
||||
category="widgets"
|
||||
switch={true}
|
||||
/>
|
||||
const AdditionalOptions = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage('modals.main.settings.additional_settings')}
|
||||
subtitle={variables.getMessage(`${SEARCH_SECTION}.additional`)}
|
||||
|
@ -108,12 +99,17 @@ export default class SearchSettings extends PureComponent {
|
|||
category="search"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const SearchEngineSelection = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${SEARCH_SECTION}.search_engine`)}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.search.search_engine_subtitle',
|
||||
)}
|
||||
final={this.state.customDisplay === 'none' ? true : false}
|
||||
final={!this.state.customEnabled}
|
||||
>
|
||||
<Dropdown
|
||||
name="searchEngine"
|
||||
|
@ -130,22 +126,37 @@ export default class SearchSettings extends PureComponent {
|
|||
</MenuItem>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
<div style={{ display: this.state.customDisplay }}>
|
||||
<SettingsItem title={variables.getMessage(`${SEARCH_SECTION}.custom`)} final={true}>
|
||||
<TextField
|
||||
label={variables.getMessage(`${SEARCH_SECTION}.custom`)}
|
||||
value={this.state.customValue}
|
||||
onInput={(e) => this.setState({ customValue: e.target.value })}
|
||||
varient="outlined"
|
||||
InputLabelProps={{ shrink: true }}
|
||||
/>
|
||||
<p style={{ marginTop: '0px' }}>
|
||||
<span className="link" onClick={() => this.resetSearch()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</p>
|
||||
</SettingsItem>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${SEARCH_SECTION}.title`)}
|
||||
setting="searchBar"
|
||||
category="widgets"
|
||||
switch={true}
|
||||
/>
|
||||
<PreferencesWrapper setting="searchBar" category="widgets" switch={true}>
|
||||
<AdditionalOptions />
|
||||
<SearchEngineSelection />
|
||||
{this.state.customEnabled && (
|
||||
<SettingsItem title={variables.getMessage(`${SEARCH_SECTION}.custom`)} final={true}>
|
||||
<TextField
|
||||
label={variables.getMessage(`${SEARCH_SECTION}.custom`)}
|
||||
value={this.state.customValue}
|
||||
onInput={(e) => this.setState({ customValue: e.target.value })}
|
||||
varient="outlined"
|
||||
InputLabelProps={{ shrink: true }}
|
||||
/>
|
||||
<p style={{ marginTop: '0px' }}>
|
||||
<span className="link" onClick={() => this.resetSearch()}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</p>
|
||||
</SettingsItem>
|
||||
)}
|
||||
</PreferencesWrapper>
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,208 +1,210 @@
|
|||
import variables from 'modules/variables';
|
||||
import { PureComponent } from 'react';
|
||||
import React, { useState } from 'react';
|
||||
|
||||
import Header from '../Header';
|
||||
import Checkbox from '../Checkbox';
|
||||
import Dropdown from '../Dropdown';
|
||||
import Radio from '../Radio';
|
||||
import SettingsItem from '../SettingsItem';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class TimeSettings extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
timeType: localStorage.getItem('timeType') || 'digital',
|
||||
hourColour: localStorage.getItem('hourColour') || '#ffffff',
|
||||
minuteColour: localStorage.getItem('minuteColour') || '#ffffff',
|
||||
};
|
||||
}
|
||||
import { MdRefresh } from 'react-icons/md';
|
||||
|
||||
updateColour(type, event) {
|
||||
const TimeSettings = () => {
|
||||
const [timeType, setTimeType] = useState(localStorage.getItem('timeType') || 'digital');
|
||||
const [hourColour, setHourColour] = useState(localStorage.getItem('hourColour') || '#ffffff');
|
||||
const [minuteColour, setMinuteColour] = useState(
|
||||
localStorage.getItem('minuteColour') || '#ffffff',
|
||||
);
|
||||
|
||||
const updateColour = (type, event) => {
|
||||
const colour = event.target.value;
|
||||
this.setState({ [type]: colour });
|
||||
if (type === 'hourColour') {
|
||||
setHourColour(colour);
|
||||
} else if (type === 'minuteColour') {
|
||||
setMinuteColour(colour);
|
||||
}
|
||||
localStorage.setItem(type, colour);
|
||||
};
|
||||
|
||||
let timeSettings = null;
|
||||
|
||||
const TIME_SECTION = 'modals.main.settings.sections.time';
|
||||
|
||||
const WidgetType = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.type`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.type_subtitle`)}
|
||||
final={timeType === 'percentageComplete'}
|
||||
>
|
||||
<Dropdown name="timeType" onChange={(value) => setTimeType(value)} category="clock">
|
||||
<option value="digital">{variables.getMessage(`${TIME_SECTION}.digital.title`)}</option>
|
||||
<option value="analogue">{variables.getMessage(`${TIME_SECTION}.analogue.title`)}</option>
|
||||
<option value="percentageComplete">
|
||||
{variables.getMessage(`${TIME_SECTION}.percentage_complete`)}
|
||||
</option>
|
||||
<option value="verticalClock">
|
||||
{variables.getMessage(`${TIME_SECTION}.vertical_clock.title`)}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const digitalSettings = (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.digital.title`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.digital.subtitle`)}
|
||||
final={true}
|
||||
>
|
||||
<Radio
|
||||
name="timeformat"
|
||||
options={[
|
||||
{
|
||||
name: variables.getMessage(`${TIME_SECTION}.digital.twentyfourhour`),
|
||||
value: 'twentyfourhour',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage(`${TIME_SECTION}.digital.twelvehour`),
|
||||
value: 'twelvehour',
|
||||
},
|
||||
]}
|
||||
smallTitle={true}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="seconds"
|
||||
text={variables.getMessage(`${TIME_SECTION}.digital.seconds`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="zero"
|
||||
text={variables.getMessage(`${TIME_SECTION}.digital.zero`)}
|
||||
category="clock"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
|
||||
const analogSettings = (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.analogue.title`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.analogue.subtitle`)}
|
||||
final={true}
|
||||
>
|
||||
<Checkbox
|
||||
name="secondHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.second_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="minuteHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.minute_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="hourHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.hour_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="hourMarks"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.hour_marks`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="minuteMarks"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.minute_marks`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="roundClock"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.round_clock`)}
|
||||
category="clock"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
|
||||
const verticalClock = (
|
||||
<>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(
|
||||
'modals.main.settings.sections.time.vertical_clock.change_hour_colour',
|
||||
)}
|
||||
>
|
||||
<div className="colourInput">
|
||||
<input
|
||||
type="color"
|
||||
name="hourColour"
|
||||
className="minuteColour"
|
||||
onChange={(event) => updateColour('hourColour', event)}
|
||||
value={hourColour}
|
||||
></input>
|
||||
<label htmlFor={'hourColour'} className="customBackgroundHex">
|
||||
{hourColour}
|
||||
</label>
|
||||
</div>
|
||||
<span className="link" onClick={() => localStorage.setItem('hourColour', '#ffffff')}>
|
||||
<MdRefresh />
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(
|
||||
'modals.main.settings.sections.time.vertical_clock.change_minute_colour',
|
||||
)}
|
||||
>
|
||||
<div className="colourInput">
|
||||
<input
|
||||
type="color"
|
||||
name="minuteColour"
|
||||
className="minuteColour"
|
||||
onChange={(event) => updateColour('minuteColour', event)}
|
||||
value={minuteColour}
|
||||
></input>
|
||||
<label htmlFor={'minuteColour'} className="customBackgroundHex">
|
||||
{minuteColour}
|
||||
</label>
|
||||
</div>
|
||||
<span className="link" onClick={() => localStorage.setItem('minuteColour', '#ffffff')}>
|
||||
<MdRefresh />
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</SettingsItem>
|
||||
{digitalSettings}
|
||||
</>
|
||||
);
|
||||
|
||||
switch (timeType) {
|
||||
case 'digital':
|
||||
timeSettings = digitalSettings;
|
||||
break;
|
||||
case 'analogue':
|
||||
timeSettings = analogSettings;
|
||||
break;
|
||||
case 'verticalClock':
|
||||
timeSettings = verticalClock;
|
||||
break;
|
||||
default:
|
||||
timeSettings = null;
|
||||
}
|
||||
|
||||
render() {
|
||||
let timeSettings = null;
|
||||
|
||||
const TIME_SECTION = 'modals.main.settings.sections.time';
|
||||
|
||||
const WidgetType = () => {
|
||||
return (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.type`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.type_subtitle`)}
|
||||
final={this.state.timeType === 'percentageComplete'}
|
||||
>
|
||||
<Dropdown
|
||||
name="timeType"
|
||||
onChange={(value) => this.setState({ timeType: value })}
|
||||
category="clock"
|
||||
>
|
||||
<option value="digital">{variables.getMessage(`${TIME_SECTION}.digital.title`)}</option>
|
||||
<option value="analogue">
|
||||
{variables.getMessage(`${TIME_SECTION}.analogue.title`)}
|
||||
</option>
|
||||
<option value="percentageComplete">
|
||||
{variables.getMessage(`${TIME_SECTION}.percentage_complete`)}
|
||||
</option>
|
||||
<option value="verticalClock">
|
||||
{variables.getMessage(`${TIME_SECTION}.vertical_clock.title`)}
|
||||
</option>
|
||||
</Dropdown>
|
||||
</SettingsItem>
|
||||
);
|
||||
};
|
||||
|
||||
const digitalSettings = (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.digital.title`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.digital.subtitle`)}
|
||||
final={true}
|
||||
>
|
||||
<Radio
|
||||
name="timeformat"
|
||||
options={[
|
||||
{
|
||||
name: variables.getMessage(`${TIME_SECTION}.digital.twentyfourhour`),
|
||||
value: 'twentyfourhour',
|
||||
},
|
||||
{
|
||||
name: variables.getMessage(`${TIME_SECTION}.digital.twelvehour`),
|
||||
value: 'twelvehour',
|
||||
},
|
||||
]}
|
||||
smallTitle={true}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="seconds"
|
||||
text={variables.getMessage(`${TIME_SECTION}.digital.seconds`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="zero"
|
||||
text={variables.getMessage(`${TIME_SECTION}.digital.zero`)}
|
||||
category="clock"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
|
||||
const analogSettings = (
|
||||
<SettingsItem
|
||||
title={variables.getMessage(`${TIME_SECTION}.analogue.title`)}
|
||||
subtitle={variables.getMessage(`${TIME_SECTION}.analogue.subtitle`)}
|
||||
final={true}
|
||||
>
|
||||
<Checkbox
|
||||
name="secondHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.second_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="minuteHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.minute_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="hourHand"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.hour_hand`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="hourMarks"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.hour_marks`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="minuteMarks"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.minute_marks`)}
|
||||
category="clock"
|
||||
/>
|
||||
<Checkbox
|
||||
name="roundClock"
|
||||
text={variables.getMessage(`${TIME_SECTION}.analogue.round_clock`)}
|
||||
category="clock"
|
||||
/>
|
||||
</SettingsItem>
|
||||
);
|
||||
|
||||
const verticalClock = (
|
||||
<>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(
|
||||
'modals.main.settings.sections.time.vertical_clock.change_hour_colour',
|
||||
)}
|
||||
>
|
||||
<div className="colourInput">
|
||||
<input
|
||||
type="color"
|
||||
name="hourColour"
|
||||
className="minuteColour"
|
||||
onChange={(event) => this.updateColour('hourColour', event)}
|
||||
value={this.state.hourColour}
|
||||
></input>
|
||||
<label htmlFor={'hourColour'} className="customBackgroundHex">
|
||||
{this.state.hourColour}
|
||||
</label>
|
||||
</div>
|
||||
<span className="link" onClick={() => localStorage.setItem('hourColour', '#ffffff')}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</SettingsItem>
|
||||
<SettingsItem
|
||||
title={variables.getMessage(
|
||||
'modals.main.settings.sections.time.vertical_clock.change_minute_colour',
|
||||
)}
|
||||
>
|
||||
<div className="colourInput">
|
||||
<input
|
||||
type="color"
|
||||
name="minuteColour"
|
||||
className="minuteColour"
|
||||
onChange={(event) => this.updateColour('minuteColour', event)}
|
||||
value={this.state.minuteColour}
|
||||
></input>
|
||||
<label htmlFor={'minuteColour'} className="customBackgroundHex">
|
||||
{this.state.minuteColour}
|
||||
</label>
|
||||
</div>
|
||||
<span className="link" onClick={() => localStorage.setItem('minuteColour', '#ffffff')}>
|
||||
{variables.getMessage('modals.main.settings.buttons.reset')}
|
||||
</span>
|
||||
</SettingsItem>
|
||||
{digitalSettings}
|
||||
</>
|
||||
);
|
||||
|
||||
switch (this.state.timeType) {
|
||||
case 'digital':
|
||||
timeSettings = digitalSettings;
|
||||
break;
|
||||
case 'analogue':
|
||||
timeSettings = analogSettings;
|
||||
break;
|
||||
case 'verticalClock':
|
||||
timeSettings = verticalClock;
|
||||
break;
|
||||
default:
|
||||
timeSettings = null;
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${TIME_SECTION}.title`)}
|
||||
setting="time"
|
||||
category="clock"
|
||||
element=".clock-container"
|
||||
zoomSetting="zoomClock"
|
||||
switch={true}
|
||||
/>
|
||||
return (
|
||||
<>
|
||||
<Header
|
||||
title={variables.getMessage(`${TIME_SECTION}.title`)}
|
||||
setting="time"
|
||||
category="clock"
|
||||
element=".clock-container"
|
||||
zoomSetting="zoomClock"
|
||||
switch={true}
|
||||
/>
|
||||
<PreferencesWrapper setting="time" zoomSetting="zoomClock" switch={true}>
|
||||
<WidgetType />
|
||||
{timeSettings}
|
||||
</>
|
||||
);
|
||||
}
|
||||
}
|
||||
</PreferencesWrapper>
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
export default TimeSettings;
|
||||
|
|
|
@ -11,7 +11,7 @@ import { TextField } from '@mui/material';
|
|||
import SettingsItem from '../SettingsItem';
|
||||
import PreferencesWrapper from '../PreferencesWrapper';
|
||||
|
||||
export default class TimeSettings extends PureComponent {
|
||||
export default class WeatherSettings extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
|
|
|
@ -205,13 +205,15 @@ export default class BackgroundSettings extends PureComponent {
|
|||
</SettingsItem>
|
||||
{this.state.backgroundAPI === 'unsplash' && (
|
||||
<SettingsItem
|
||||
title="Unsplash Collection(s)"
|
||||
subtitle="Select the collection(s) you want to use for your background"
|
||||
title={variables.getMessage('modals.main.settings.sections.background.unsplash.title')}
|
||||
subtitle={variables.getMessage('modals.main.settings.sections.background.subtitle')}
|
||||
final={true}
|
||||
>
|
||||
<Text
|
||||
title="Collection ID(s)"
|
||||
subtitle="Enter the collection ID(s) you want to use for your background"
|
||||
title={variables.getMessage('modals.main.settings.sections.background.id')}
|
||||
subtitle={variables.getMessage(
|
||||
'modals.main.settings.sections.background.id_subtitle',
|
||||
)}
|
||||
placeholder="e.g. 123456, 654321"
|
||||
name="unsplashCollections"
|
||||
category="background"
|
||||
|
|
|
@ -1,28 +0,0 @@
|
|||
const getTitleFromUrl = async (url) => {
|
||||
let title;
|
||||
try {
|
||||
let response = await fetch(url);
|
||||
if (response.redirected) {
|
||||
response = await fetch(response.url);
|
||||
}
|
||||
const html = await response.text();
|
||||
const parser = new DOMParser();
|
||||
const doc = parser.parseFromString(html, 'text/html');
|
||||
title = doc.title;
|
||||
} catch (e) {
|
||||
title = url;
|
||||
}
|
||||
|
||||
return title;
|
||||
};
|
||||
|
||||
const isValidUrl = (url) => {
|
||||
// regex: https://ihateregex.io/expr/url/
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
const urlRegex =
|
||||
/https?:\/\/(www\.)?[-a-zA-Z0-9@:%._~#=]{1,256}\.[a-zA-Z0-9()]{1,6}\b([-a-zA-Z0-9()!@:%_.~#?&=]*)/;
|
||||
|
||||
return urlRegex.test(url);
|
||||
};
|
||||
|
||||
export { getTitleFromUrl, isValidUrl };
|
|
@ -0,0 +1,147 @@
|
|||
// TODO: make it work with pins or on click or smth
|
||||
import variables from 'modules/variables';
|
||||
import { PureComponent, memo, useState } from 'react';
|
||||
|
||||
import { MdLinkOff, MdOutlineApps } from 'react-icons/md';
|
||||
import Tooltip from 'components/helpers/tooltip/Tooltip';
|
||||
import { shift, useFloating } from '@floating-ui/react-dom';
|
||||
import EventBus from 'modules/helpers/eventbus';
|
||||
|
||||
class Apps extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
apps: JSON.parse(localStorage.getItem('applinks')),
|
||||
visibility: localStorage.getItem('appsPinned') === 'true' ? 'visible' : 'hidden',
|
||||
marginLeft: localStorage.getItem('refresh') === 'false' ? '-200px' : '-130px',
|
||||
showApps: localStorage.getItem('appsPinned') === 'true',
|
||||
};
|
||||
}
|
||||
|
||||
setZoom() {
|
||||
this.setState({
|
||||
zoomFontSize: Number(((localStorage.getItem('zoomNavbar') || 100) / 100) * 1.2) + 'rem',
|
||||
});
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
EventBus.on('refresh', (data) => {
|
||||
if (data === 'navbar') {
|
||||
this.forceUpdate();
|
||||
try {
|
||||
this.setZoom();
|
||||
} catch (e) {}
|
||||
}
|
||||
});
|
||||
|
||||
this.setZoom();
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
EventBus.off('refresh');
|
||||
}
|
||||
|
||||
showApps() {
|
||||
this.setState({
|
||||
showApps: true,
|
||||
});
|
||||
}
|
||||
|
||||
hideApps() {
|
||||
this.setState({
|
||||
showApps: localStorage.getItem('AppsPinned') === 'true',
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
const appsInfo = this.state.apps;
|
||||
|
||||
return (
|
||||
<div className="notes" onMouseLeave={() => this.hideApps()} onFocus={() => this.showApps()}>
|
||||
<button
|
||||
className="first"
|
||||
onMouseEnter={() => this.showApps()}
|
||||
onFocus={() => this.hideApps()}
|
||||
onBlur={() => this.showApps()}
|
||||
ref={this.props.appsRef}
|
||||
style={{ fontSize: this.state.zoomFontSize }}
|
||||
>
|
||||
<MdOutlineApps className="topicons" />
|
||||
</button>
|
||||
{this.state.showApps && (
|
||||
<span
|
||||
className="notesContainer"
|
||||
ref={this.props.floatRef}
|
||||
style={{
|
||||
position: this.props.position,
|
||||
top: this.props.yPosition ?? '44px',
|
||||
left: this.props.xPosition ?? '',
|
||||
}}
|
||||
>
|
||||
{appsInfo.length > 0 ? (
|
||||
<div className="appsShortcutContainer">
|
||||
{appsInfo.map((info, i) => (
|
||||
<Tooltip
|
||||
title={info.name.split(' ')[0]}
|
||||
subtitle={info.name.split(' ').slice(1).join(' ')}
|
||||
key={i}
|
||||
>
|
||||
<a href={info.url} className="appsIcon">
|
||||
<img
|
||||
src={
|
||||
info.icon === ''
|
||||
? `https://icon.horse/icon/ ${info.url.replace('https://', '').replace('http://', '')}`
|
||||
: info.icon
|
||||
}
|
||||
width="40px"
|
||||
height="40px"
|
||||
alt="Google"
|
||||
/>
|
||||
<span>{info.name}</span>
|
||||
</a>
|
||||
</Tooltip>
|
||||
))}
|
||||
</div>
|
||||
) : (
|
||||
<div className="noAppsContainer">
|
||||
<div className="emptyNewMessage">
|
||||
<MdLinkOff />
|
||||
<span className="title">
|
||||
{variables.language.getMessage(
|
||||
variables.languagecode,
|
||||
'widgets.navbar.apps.no_apps',
|
||||
)}
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</span>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
function AppsWrapper() {
|
||||
const [reference, setReference] = useState(null);
|
||||
|
||||
const { x, y, refs, strategy } = useFloating({
|
||||
placement: 'bottom',
|
||||
middleware: [shift()],
|
||||
elements: {
|
||||
reference,
|
||||
},
|
||||
});
|
||||
|
||||
return (
|
||||
<Apps
|
||||
appsRef={setReference}
|
||||
floatRef={refs.setFloating}
|
||||
position={strategy}
|
||||
xPosition={x}
|
||||
yPosition={y}
|
||||
/>
|
||||
);
|
||||
}
|
||||
|
||||
export default memo(AppsWrapper);
|
|
@ -1,10 +1,11 @@
|
|||
import variables from 'modules/variables';
|
||||
import { PureComponent, createRef } from 'react';
|
||||
|
||||
import { MdRefresh, MdSettings, MdOutlineApps } from 'react-icons/md';
|
||||
import { MdRefresh, MdSettings } from 'react-icons/md';
|
||||
|
||||
import Notes from './Notes';
|
||||
import Todo from './Todo';
|
||||
import Apps from './Apps';
|
||||
import Maximise from '../background/Maximise';
|
||||
import Tooltip from 'components/helpers/tooltip/Tooltip';
|
||||
|
||||
|
@ -109,6 +110,9 @@ class Navbar extends PureComponent {
|
|||
{localStorage.getItem('todoEnabled') === 'true' && (
|
||||
<Todo fontSize={this.state.zoomFontSize} />
|
||||
)}
|
||||
{localStorage.getItem('appsEnabled') === 'true' && (
|
||||
<Apps fontSize={this.state.zoomFontSize} />
|
||||
)}
|
||||
|
||||
{this.refreshEnabled !== 'false' && (
|
||||
<Tooltip
|
||||
|
@ -125,20 +129,6 @@ class Navbar extends PureComponent {
|
|||
</Tooltip>
|
||||
)}
|
||||
|
||||
{localStorage.getItem('appsEnabled') === 'true' && (
|
||||
<>
|
||||
<Tooltip title={variables.getMessage('widgets.navbar.apps.title')}>
|
||||
<button
|
||||
style={{ fontSize: this.state.zoomFontSize }}
|
||||
onClick={() => this.props.openModal('appsModal')}
|
||||
id="appsShortcutBtn"
|
||||
>
|
||||
<MdOutlineApps className="topicons" />
|
||||
</button>
|
||||
</Tooltip>
|
||||
</>
|
||||
)}
|
||||
|
||||
<Tooltip
|
||||
title={variables.getMessage('modals.main.navbar.settings', {
|
||||
type: variables.getMessage(
|
||||
|
|
|
@ -20,6 +20,8 @@ $appsWidth: 21rem;
|
|||
}
|
||||
|
||||
.noAppsContainer {
|
||||
grid-column: 1/3;
|
||||
|
||||
h3 {
|
||||
margin: 0;
|
||||
display: flex;
|
|
@ -1,5 +1,6 @@
|
|||
@import 'notes';
|
||||
@import 'todo';
|
||||
@import 'apps';
|
||||
@import 'scss/variables';
|
||||
|
||||
.navbar {
|
||||
|
|
|
@ -17,7 +17,7 @@ const convertTemperature = (temp, format) => {
|
|||
return Math.round(temp);
|
||||
};
|
||||
|
||||
export default class Weather extends PureComponent {
|
||||
export default class WeatherSettings extends PureComponent {
|
||||
constructor() {
|
||||
super();
|
||||
this.state = {
|
||||
|
|
|
@ -121,3 +121,30 @@ export function values(type) {
|
|||
|
||||
return marks[type] || [];
|
||||
}
|
||||
|
||||
export async function getTitleFromUrl(url) {
|
||||
let title;
|
||||
try {
|
||||
let response = await fetch(url);
|
||||
if (response.redirected) {
|
||||
response = await fetch(response.url);
|
||||
}
|
||||
const html = await response.text();
|
||||
const parser = new DOMParser();
|
||||
const doc = parser.parseFromString(html, 'text/html');
|
||||
title = doc.title;
|
||||
} catch (e) {
|
||||
title = url;
|
||||
}
|
||||
|
||||
return title;
|
||||
}
|
||||
|
||||
export function isValidUrl(url) {
|
||||
// regex: https://ihateregex.io/expr/url/
|
||||
// eslint-disable-next-line no-useless-escape
|
||||
const urlRegex =
|
||||
/https?:\/\/(www\.)?[-a-zA-Z0-9@:%._~#=]{1,256}\.[a-zA-Z0-9()]{1,6}\b([-a-zA-Z0-9()!@:%_.~#?&=]*)/;
|
||||
|
||||
return urlRegex.test(url);
|
||||
}
|
||||
|
|
|
@ -129,7 +129,12 @@ body {
|
|||
}
|
||||
}
|
||||
|
||||
.inactiveSetting {
|
||||
.preferences {
|
||||
transition: 0.4s ease-in-out;
|
||||
}
|
||||
|
||||
.preferencesInactive {
|
||||
opacity: 0.5;
|
||||
pointer-events: none;
|
||||
transition: 0.4s ease-in-out;
|
||||
}
|
||||
|
|
|
@ -266,13 +266,13 @@
|
|||
"search": {
|
||||
"title": "Search",
|
||||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Search engine",
|
||||
"search_engine": "Search Engine",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "Custom search URL",
|
||||
"custom": "Custom Search URL",
|
||||
"autocomplete": "Autocomplete",
|
||||
"autocomplete_provider": "Autocomplete Provider",
|
||||
"autocomplete_provider_subtitle": "Search engine to use for autocomplete dropdown results",
|
||||
"voice_search": "Voice search",
|
||||
"voice_search": "Voice Search",
|
||||
"dropdown": "Search dropdown",
|
||||
"focus": "Focus on tab open"
|
||||
},
|
||||
|
@ -354,7 +354,7 @@
|
|||
"navbar": {
|
||||
"title": "Navbar",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_subtitle": "Choose what is refreshed when you click the refresh button",
|
||||
"hover": "Only display on hover",
|
||||
"additional": "Modify navbar style and which buttons you want to display",
|
||||
|
@ -396,8 +396,8 @@
|
|||
"old": "Old",
|
||||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"toast_duration": "Toast duration",
|
||||
"widget_zoom": "Widget Zoom",
|
||||
"toast_duration": "Toast Duration",
|
||||
"milliseconds": "milliseconds"
|
||||
}
|
||||
},
|
||||
|
|
|
@ -226,6 +226,12 @@
|
|||
"random_colour": "Random colour",
|
||||
"random_gradient": "Random gradient"
|
||||
},
|
||||
"unsplash": {
|
||||
"title": "Unsplash Collection(s)",
|
||||
"subtitle": "Select the collection(s) you want to use for your background",
|
||||
"id": "Collection ID(s)",
|
||||
"id_subtitle": "Enter a comma separated list of Unsplash IDs"
|
||||
},
|
||||
"source": {
|
||||
"title": "Source",
|
||||
"subtitle": "Select where to get background images from",
|
||||
|
@ -270,14 +276,14 @@
|
|||
"search": {
|
||||
"title": "Search",
|
||||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Search engine",
|
||||
"search_engine": "Search Engine",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "Custom search URL",
|
||||
"custom": "Custom Search URL",
|
||||
"autocomplete": "Autocomplete",
|
||||
"autocomplete_provider": "Autocomplete Provider",
|
||||
"autocomplete_provider_subtitle": "Search engine to use for autocomplete dropdown results",
|
||||
"voice_search": "Voice search",
|
||||
"dropdown": "Search dropdown",
|
||||
"dropdown": "Search Dropdown",
|
||||
"focus": "Focus on tab open"
|
||||
},
|
||||
"weather": {
|
||||
|
@ -328,7 +334,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
@ -358,7 +364,7 @@
|
|||
"navbar": {
|
||||
"title": "Navbar",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_subtitle": "Choose what is refreshed when you click the refresh button",
|
||||
"hover": "Only display on hover",
|
||||
"additional": "Modify navbar style and which buttons you want to display",
|
||||
|
@ -401,8 +407,8 @@
|
|||
"old": "Old",
|
||||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"toast_duration": "Toast duration",
|
||||
"widget_zoom": "Widget Zoom",
|
||||
"toast_duration": "Toast Duration",
|
||||
"milliseconds": "milliseconds"
|
||||
}
|
||||
},
|
||||
|
|
|
@ -270,14 +270,14 @@
|
|||
"search": {
|
||||
"title": "Search",
|
||||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Search engine",
|
||||
"search_engine": "Search Engine",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "Custom search URL",
|
||||
"custom": "Custom Search URL",
|
||||
"autocomplete": "Autocomplete",
|
||||
"autocomplete_provider": "Autocomplete Provider",
|
||||
"autocomplete_provider_subtitle": "Search engine to use for autocomplete dropdown results",
|
||||
"voice_search": "Voice search",
|
||||
"dropdown": "Search dropdown",
|
||||
"voice_search": "Voice Search",
|
||||
"dropdown": "Search Dropdown",
|
||||
"focus": "Focus on tab open"
|
||||
},
|
||||
"weather": {
|
||||
|
@ -328,7 +328,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
@ -358,7 +358,7 @@
|
|||
"navbar": {
|
||||
"title": "Navbar",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_subtitle": "Choose what is refreshed when you click the refresh button",
|
||||
"hover": "Only display on hover",
|
||||
"additional": "Modify navbar style and which buttons you want to display",
|
||||
|
@ -402,7 +402,7 @@
|
|||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"toast_duration": "Toast duration",
|
||||
"toast_duration": "Toast Duration",
|
||||
"milliseconds": "milliseconds"
|
||||
}
|
||||
},
|
||||
|
|
|
@ -266,7 +266,7 @@
|
|||
"search": {
|
||||
"title": "Búsqueda",
|
||||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Motor de búsqueda",
|
||||
"search_engine": "Motor de Búsqueda",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "URL de búsqueda personalizada",
|
||||
"autocomplete": "Autocompletado",
|
||||
|
@ -324,7 +324,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
|
|
@ -266,7 +266,7 @@
|
|||
"search": {
|
||||
"title": "Barre de Recherche",
|
||||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Moteur de recherche",
|
||||
"search_engine": "Moteur de Recherche",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "URL de recherche personnalisée",
|
||||
"autocomplete": "Autocomplete",
|
||||
|
@ -324,7 +324,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
@ -354,7 +354,7 @@
|
|||
"navbar": {
|
||||
"title": "Navbar",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_subtitle": "Choose what is refreshed when you click the refresh button",
|
||||
"hover": "Only display on hover",
|
||||
"additional": "Modify navbar style and which buttons you want to display",
|
||||
|
|
|
@ -268,7 +268,7 @@
|
|||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Mesin pencari",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "URL kustom",
|
||||
"custom": "URL Kustom",
|
||||
"autocomplete": "Autocomplete",
|
||||
"autocomplete_provider": "Provider Autocomplete",
|
||||
"autocomplete_provider_subtitle": "Search engine to use for autocomplete dropdown results",
|
||||
|
@ -324,7 +324,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
@ -396,7 +396,7 @@
|
|||
"old": "Old",
|
||||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"widget_zoom": "Widget Zoom",
|
||||
"toast_duration": "Durasi toast",
|
||||
"milliseconds": "milliseconds"
|
||||
}
|
||||
|
|
|
@ -174,8 +174,8 @@
|
|||
"title": "Widget text shadow"
|
||||
},
|
||||
"title": "Accessibility",
|
||||
"toast_duration": "Toast duration",
|
||||
"widget_zoom": "Widget zoom"
|
||||
"toast_duration": "Toast Duration",
|
||||
"widget_zoom": "Widget Zoom"
|
||||
},
|
||||
"font": {
|
||||
"custom": "Custom font",
|
||||
|
@ -205,7 +205,7 @@
|
|||
"apps_subtitle": "Maak een snelkoppeling van je andere vaak gebruikte websites.",
|
||||
"hover": "Only display on hover",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_options": {
|
||||
"none": "None",
|
||||
"page": "Page"
|
||||
|
|
|
@ -268,7 +268,7 @@
|
|||
"additional": "Additional options for search widget display and functionality",
|
||||
"search_engine": "Søkemotor",
|
||||
"search_engine_subtitle": "Choose search engine to use in the search bar",
|
||||
"custom": "Custom search URL",
|
||||
"custom": "Custom Search",
|
||||
"autocomplete": "Autocomplete",
|
||||
"autocomplete_provider": "Autocomplete Provider",
|
||||
"autocomplete_provider_subtitle": "Search engine to use for autocomplete dropdown results",
|
||||
|
@ -324,7 +324,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
@ -354,7 +354,7 @@
|
|||
"navbar": {
|
||||
"title": "Navbar",
|
||||
"notes": "Notes",
|
||||
"refresh": "Refresh button",
|
||||
"refresh": "Refresh Button",
|
||||
"refresh_subtitle": "Choose what is refreshed when you click the refresh button",
|
||||
"hover": "Only display on hover",
|
||||
"additional": "Modify navbar style and which buttons you want to display",
|
||||
|
@ -396,8 +396,8 @@
|
|||
"old": "Old",
|
||||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"toast_duration": "Toast duration",
|
||||
"widget_zoom": "Widget Zoom",
|
||||
"toast_duration": "Toast Duration",
|
||||
"milliseconds": "milliseconds"
|
||||
}
|
||||
},
|
||||
|
|
|
@ -396,7 +396,7 @@
|
|||
"old": "Old",
|
||||
"none": "None"
|
||||
},
|
||||
"widget_zoom": "Widget zoom",
|
||||
"widget_zoom": "Widget Zoom",
|
||||
"toast_duration": "Продолжительность подсказки",
|
||||
"milliseconds": "миллисекунды"
|
||||
}
|
||||
|
|
|
@ -324,7 +324,7 @@
|
|||
"text_only": "Text Only",
|
||||
"metro": "Metro"
|
||||
},
|
||||
"styling": "Quick Links Styling",
|
||||
"styling": "Styling",
|
||||
"styling_description": "Customise Quick Links appearance"
|
||||
},
|
||||
"message": {
|
||||
|
|
Loading…
Reference in New Issue