mirror of
https://github.com/mue/mue.git
synced 2026-06-08 14:10:42 +02:00
soon
This commit is contained in:
25
src/App.jsx
25
src/App.jsx
@@ -29,18 +29,31 @@ export default class App extends React.PureComponent {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (!localStorage.getItem('firstRun')) SettingsFunctions.setDefaultSettings();
|
||||
if (localStorage.getItem('showWelcome') === 'true') this.setState({ welcomeModal: true });
|
||||
if (!localStorage.getItem('firstRun')) {
|
||||
SettingsFunctions.setDefaultSettings();
|
||||
}
|
||||
|
||||
if (localStorage.getItem('showWelcome') === 'true') {
|
||||
this.setState({
|
||||
welcomeModal: true
|
||||
});
|
||||
}
|
||||
|
||||
const css = localStorage.getItem('customcss');
|
||||
if (css) document.head.insertAdjacentHTML('beforeend', '<style>' + css + '</style>');
|
||||
if (css) {
|
||||
document.head.insertAdjacentHTML('beforeend', '<style>' + css + '</style>');
|
||||
}
|
||||
|
||||
if (localStorage.getItem('darkTheme') === 'true') document.getElementsByClassName('Toastify')[0].classList.add('dark');
|
||||
if (localStorage.getItem('darkTheme') === 'true'){
|
||||
document.getElementsByClassName('Toastify')[0].classList.add('dark');
|
||||
}
|
||||
}
|
||||
|
||||
closeWelcome() {
|
||||
localStorage.setItem('showWelcome', false);
|
||||
this.setState({ welcomeModal: false });
|
||||
this.setState({
|
||||
welcomeModal: false
|
||||
});
|
||||
}
|
||||
|
||||
// Render all the components
|
||||
@@ -48,10 +61,12 @@ export default class App extends React.PureComponent {
|
||||
// dark theme support for modals and info card
|
||||
let modalClassList = 'Modal';
|
||||
let tooltipClassList = 'infoCard';
|
||||
|
||||
if ((localStorage.getItem('brightnessTime') && new Date().getHours() > 18) || localStorage.getItem('darkTheme') === 'true') {
|
||||
modalClassList += ' dark';
|
||||
tooltipClassList += ' dark';
|
||||
}
|
||||
|
||||
const overlayClassList = (localStorage.getItem('animations') === 'true') ? 'Overlay modal-animation' : 'Overlay';
|
||||
|
||||
/// language
|
||||
|
||||
@@ -9,23 +9,26 @@ import AddonsIcon from '@material-ui/icons/Widgets';
|
||||
import MarketplaceIcon from '@material-ui/icons/ShoppingBasket';
|
||||
|
||||
export default class MainModal extends React.PureComponent {
|
||||
constructor(...args) {
|
||||
super(...args);
|
||||
this.state = {
|
||||
tab: '',
|
||||
currentTab: ''
|
||||
};
|
||||
this.tabs = {
|
||||
settings: <Settings language={this.props.language.settings} toastLanguage={this.props.language.toasts} />,
|
||||
addons: <Addons language={this.props.language.addons} marketplaceLanguage={this.props.language.marketplace} toastLanguage={this.props.language.toasts} openMarketplace={() => this.changeEnabled('marketplace')}/>,
|
||||
marketplace: <Marketplace language={this.props.language.marketplace} toastLanguage={this.props.language.toasts} updateLanguage={this.props.language.update}/>
|
||||
}
|
||||
constructor(...args) {
|
||||
super(...args);
|
||||
this.state = {
|
||||
tab: '',
|
||||
currentTab: ''
|
||||
}
|
||||
this.tabs = {
|
||||
settings: <Settings language={this.props.language.settings} toastLanguage={this.props.language.toasts} />,
|
||||
addons: <Addons language={this.props.language.addons} marketplaceLanguage={this.props.language.marketplace} toastLanguage={this.props.language.toasts} openMarketplace={() => this.changeEnabled('marketplace')}/>,
|
||||
marketplace: <Marketplace language={this.props.language.marketplace} toastLanguage={this.props.language.toasts} updateLanguage={this.props.language.update}/>
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
document.getElementById('backgroundImage').classList.toggle('backgroundEffects');
|
||||
document.getElementById('center').classList.toggle('backgroundEffects');
|
||||
this.setState({ tab: this.tabs.settings, currentTab: 'settings' });
|
||||
|
||||
this.setState({
|
||||
tab: this.tabs.settings, currentTab: 'settings'
|
||||
});
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
@@ -36,7 +39,10 @@ export default class MainModal extends React.PureComponent {
|
||||
changeEnabled(input) {
|
||||
document.getElementById(this.state.currentTab + 'TabLink').classList.toggle('active');
|
||||
document.getElementById(input + 'TabLink').classList.toggle('active');
|
||||
this.setState({ tab: this.tabs[input], currentTab: input });
|
||||
|
||||
this.setState({
|
||||
tab: this.tabs[input], currentTab: input
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
|
||||
@@ -22,6 +22,7 @@ export default class Update extends React.PureComponent {
|
||||
}
|
||||
|
||||
const data = await (await fetch(Constants.API_URL + '/getUpdate')).json();
|
||||
|
||||
if (data.statusCode === 500 || data.title === null) {
|
||||
const supportText = `<br/><p>${this.props.language.contact_support}: <a target='_blank' class='modalLink' href='https://muetab.com/contact'>https://muetab.com/contact</a></p>`;
|
||||
return this.setState({
|
||||
|
||||
@@ -15,7 +15,9 @@ export default class Item extends React.PureComponent {
|
||||
</div>
|
||||
);
|
||||
}
|
||||
} catch (e) {}
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
|
||||
return (
|
||||
<div id='item'>
|
||||
|
||||
@@ -2,10 +2,14 @@ import React from 'react';
|
||||
|
||||
export default class Items extends React.PureComponent {
|
||||
render() {
|
||||
if (this.props.items.length === 0) return null; // if there are no items in category don't render it
|
||||
if (this.props.items.length === 0) {
|
||||
return null; // if there are no items in category don't render it
|
||||
}
|
||||
|
||||
let seeMoreHTML;
|
||||
if (this.props.seeMoreFunction && this.props.items.length === 3) seeMoreHTML = <button className='addToMue seemore' onClick={this.props.seeMoreFunction}>{this.props.seeMoreTitle}</button>; // only render see more button if there are enough addons
|
||||
if (this.props.seeMoreFunction && this.props.items.length === 3) {
|
||||
seeMoreHTML = <button className='addToMue seemore' onClick={this.props.seeMoreFunction}>{this.props.seeMoreTitle}</button>; // only render see more button if there are enough addons
|
||||
}
|
||||
|
||||
return (
|
||||
<div>
|
||||
|
||||
@@ -13,13 +13,19 @@ export default class Checkbox extends React.PureComponent {
|
||||
|
||||
handleChange(name) {
|
||||
SettingsFunctions.setItem(name);
|
||||
this.setState({ checked: (this.state.checked === true) ? false : true });
|
||||
this.setState({
|
||||
checked: (this.state.checked === true) ? false : true
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
let text = this.props.text;
|
||||
if (this.props.newFeature) text = <span>{this.props.text} <span className='newFeature'> NEW</span></span>;
|
||||
else if (this.props.betaFeature) text = <span>{this.props.text} <span className='newFeature'> BETA</span></span>;
|
||||
|
||||
if (this.props.newFeature) {
|
||||
text = <span>{this.props.text} <span className='newFeature'> NEW</span></span>;
|
||||
} else if (this.props.betaFeature) {
|
||||
text = <span>{this.props.text} <span className='newFeature'> BETA</span></span>;
|
||||
}
|
||||
|
||||
return (
|
||||
<React.Fragment>
|
||||
|
||||
@@ -7,9 +7,12 @@ export default class FileUpload extends React.PureComponent {
|
||||
const reader = new FileReader();
|
||||
const file = e.target.files[0];
|
||||
|
||||
if (this.props.type === 'settings') reader.readAsText(file, 'UTF-8');
|
||||
else { // background upload
|
||||
if (file.size > 2000000) return toast('File is over 2MB');
|
||||
if (this.props.type === 'settings') {
|
||||
reader.readAsText(file, 'UTF-8');
|
||||
} else { // background upload
|
||||
if (file.size > 2000000) {
|
||||
return toast('File is over 2MB');
|
||||
}
|
||||
reader.readAsDataURL(file);
|
||||
}
|
||||
reader.addEventListener('load', (e) => this.props.loadFunction(e));
|
||||
|
||||
@@ -19,7 +19,9 @@ export default class Section extends React.PureComponent {
|
||||
transform: (this.state.transform === 'rotate(0)') ? 'rotate(-180deg)' : 'rotate(0)'
|
||||
});
|
||||
|
||||
if (this.props.onToggle) this.props.onToggle(display);
|
||||
if (this.props.onToggle) {
|
||||
this.props.onToggle(display);
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
@@ -31,6 +33,7 @@ export default class Section extends React.PureComponent {
|
||||
<li className='extraSettings'>{this.props.children}</li>
|
||||
</div>
|
||||
);
|
||||
|
||||
expandMore = (
|
||||
<ExpandMore
|
||||
style={{ 'transition': 'all 0.5s ease 0s', 'transform': this.state.transform }}
|
||||
@@ -38,8 +41,14 @@ export default class Section extends React.PureComponent {
|
||||
onClick={() => this.toggleSection()} />
|
||||
);
|
||||
}
|
||||
if (this.props.slider !== false) slider = <Slider name={this.props.name} />;
|
||||
if (this.props.dropdown === false) noDropdown = 'nodropdown';
|
||||
|
||||
if (this.props.slider !== false) {
|
||||
slider = <Slider name={this.props.name} />;
|
||||
}
|
||||
|
||||
if (this.props.dropdown === false){
|
||||
noDropdown = 'nodropdown';
|
||||
}
|
||||
|
||||
return (
|
||||
<div className='section'>
|
||||
|
||||
@@ -11,11 +11,14 @@ export default class Slider extends React.PureComponent {
|
||||
|
||||
handleChange(name) {
|
||||
SettingsFunctions.setItem(name);
|
||||
this.setState({ checked: (this.state.checked === true) ? false : true });
|
||||
this.setState({
|
||||
checked: (this.state.checked === true) ? false : true
|
||||
});
|
||||
}
|
||||
|
||||
render() {
|
||||
let setText = (this.props.override) ? this.props.override : this.props.name;
|
||||
|
||||
return (
|
||||
<label className='switch'>
|
||||
<input type='checkbox' checked={this.state.checked} onChange={() => this.handleChange(setText)} />
|
||||
|
||||
@@ -34,19 +34,33 @@ export default class BackgroundSettings extends React.PureComponent {
|
||||
switch (key) {
|
||||
case 'customBackgroundColour':
|
||||
localStorage.setItem('customBackgroundColour', '');
|
||||
this.setState({ gradientSettings: this.DefaultGradientSettings });
|
||||
this.setState({
|
||||
gradientSettings: this.DefaultGradientSettings
|
||||
});
|
||||
break;
|
||||
case 'customBackground': document.getElementById('customBackground').value = ''; break;
|
||||
|
||||
case 'customBackground':
|
||||
document.getElementById('customBackground').value = '';
|
||||
break;
|
||||
|
||||
case 'blur':
|
||||
localStorage.setItem('blur', 0);
|
||||
this.setState({ blur: 0 });
|
||||
this.setState({
|
||||
blur: 0
|
||||
});
|
||||
break;
|
||||
|
||||
case 'brightness':
|
||||
localStorage.setItem('brightness', 100);
|
||||
this.setState({ brightness: 100 });
|
||||
this.setState({
|
||||
brightness: 100
|
||||
});
|
||||
break;
|
||||
default: toast('resetItem requires a key!');
|
||||
|
||||
default:
|
||||
toast('resetItem requires a key!');
|
||||
}
|
||||
|
||||
toast(this.props.toastLanguage.reset);
|
||||
}
|
||||
|
||||
@@ -79,7 +93,9 @@ export default class BackgroundSettings extends React.PureComponent {
|
||||
}
|
||||
}
|
||||
|
||||
if (gradientSettings === undefined) gradientSettings = this.DefaultGradientSettings;
|
||||
if (gradientSettings === undefined) {
|
||||
gradientSettings = this.DefaultGradientSettings;
|
||||
}
|
||||
|
||||
this.setState({
|
||||
blur: localStorage.getItem('blur'),
|
||||
@@ -129,9 +145,20 @@ export default class BackgroundSettings extends React.PureComponent {
|
||||
}
|
||||
|
||||
onColorPickerChange = (attrs, name) => {
|
||||
if (process.env.NODE_ENV === 'development') console.log(attrs, name);
|
||||
if (process.env.NODE_ENV === 'development') {
|
||||
console.log(attrs, name);
|
||||
}
|
||||
|
||||
this.setState({
|
||||
gradientSettings: { 'angle': attrs.degree, 'gradient': attrs.points.map((p) => { return { 'colour': '#' + rgbToHex(p.red, p.green, p.blue), 'stop': p.left } }), 'type': attrs.type }
|
||||
gradientSettings: {
|
||||
'angle': attrs.degree,
|
||||
'gradient': attrs.points.map((p) => {
|
||||
return {
|
||||
'colour': '#' + rgbToHex(p.red, p.green, p.blue),
|
||||
'stop': p.left
|
||||
} }),
|
||||
'type': attrs.type
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
@@ -145,7 +172,9 @@ export default class BackgroundSettings extends React.PureComponent {
|
||||
|
||||
fileUpload(e) {
|
||||
localStorage.setItem('customBackground', e.target.result);
|
||||
this.setState({ customBackground: e.target.result });
|
||||
this.setState({
|
||||
customBackground: e.target.result
|
||||
});
|
||||
}
|
||||
|
||||
beforeUnload() {
|
||||
|
||||
@@ -20,9 +20,14 @@ export default class GreetingSettings extends React.PureComponent {
|
||||
}
|
||||
|
||||
changeDate(data) {
|
||||
if (data === 'reset') return; //soon
|
||||
if (data === 'reset') {
|
||||
return; //soon
|
||||
}
|
||||
|
||||
localStorage.setItem('birthday', data);
|
||||
this.setState({ birthday: data });
|
||||
this.setState({
|
||||
birthday: data
|
||||
});
|
||||
}
|
||||
|
||||
beforeUnload() {
|
||||
|
||||
@@ -16,12 +16,17 @@ export default class SearchSettings extends React.PureComponent {
|
||||
|
||||
componentDidMount() {
|
||||
const searchEngine = localStorage.getItem('searchEngine');
|
||||
|
||||
if (searchEngine === 'custom') {
|
||||
const input = document.getElementById('searchEngineInput');
|
||||
|
||||
input.style.display = 'block';
|
||||
input.enabled = 'true';
|
||||
|
||||
document.getElementById('customSearchEngine').value = localStorage.getItem('customSearchEngine');
|
||||
} else localStorage.removeItem('customSearchEngine');
|
||||
} else {
|
||||
localStorage.removeItem('customSearchEngine');
|
||||
}
|
||||
|
||||
document.getElementById('searchEngine').value = searchEngine;
|
||||
}
|
||||
|
||||
@@ -35,8 +35,13 @@ export default class Addons extends React.PureComponent {
|
||||
if (type === 'item') {
|
||||
const installed = JSON.parse(localStorage.getItem('installed'));
|
||||
const info = installed.find(i => i.name === data);
|
||||
|
||||
this.setState({
|
||||
current_data: { type: type2, name: data, content: info },
|
||||
current_data: {
|
||||
type: type2,
|
||||
name: data,
|
||||
content: info
|
||||
},
|
||||
item_data: {
|
||||
name: info.name,
|
||||
author: info.author,
|
||||
@@ -53,23 +58,40 @@ export default class Addons extends React.PureComponent {
|
||||
document.getElementById('marketplace').style.display = 'block';
|
||||
document.getElementById('item').style.display = 'none';
|
||||
}
|
||||
this.setState({ button: this.buttons.uninstall });
|
||||
this.setState({
|
||||
button: this.buttons.uninstall
|
||||
});
|
||||
}
|
||||
|
||||
manage(type, input) {
|
||||
switch (type) {
|
||||
case 'install': MarketplaceFunctions.install(input.type, input, true); break;
|
||||
case 'uninstall': MarketplaceFunctions.uninstall(this.state.current_data.name, this.state.current_data.content.type); break;
|
||||
default: break;
|
||||
case 'install':
|
||||
MarketplaceFunctions.install(input.type, input, true);
|
||||
break;
|
||||
case 'uninstall':
|
||||
MarketplaceFunctions.uninstall(this.state.current_data.name, this.state.current_data.content.type);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
toast(this.props.toastLanguage[type + 'ed']);
|
||||
|
||||
let button = '';
|
||||
if (type === 'install') button = this.buttons.uninstall;
|
||||
this.setState({ button: button, installed: JSON.parse(localStorage.getItem('installed')) });
|
||||
if (type === 'install'){
|
||||
button = this.buttons.uninstall;
|
||||
}
|
||||
|
||||
this.setState({
|
||||
button: button,
|
||||
installed: JSON.parse(localStorage.getItem('installed'))
|
||||
});
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('animations') === 'true') document.getElementById('marketplace').classList.add('marketplaceanimation');
|
||||
if (localStorage.getItem('animations') === 'true') {
|
||||
document.getElementById('marketplace').classList.add('marketplaceanimation');
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
|
||||
@@ -44,12 +44,20 @@ export default class Marketplace extends React.PureComponent {
|
||||
case 'seemore':
|
||||
document.getElementById('marketplace').style.display = 'none';
|
||||
document.getElementById('seemore').style.display = 'block';
|
||||
this.setState({ see_more: this.state[type2], see_more_type: type2 });
|
||||
|
||||
this.setState({
|
||||
see_more: this.state[type2],
|
||||
see_more_type: type2
|
||||
});
|
||||
break;
|
||||
|
||||
case 'item':
|
||||
let info;
|
||||
try { info = await (await fetch(`${Constants.MARKETPLACE_URL}/item/${type2}/${data}`)).json(); }
|
||||
catch (e) { return toast(this.props.toastLanguage.error); }
|
||||
try {
|
||||
info = await (await fetch(`${Constants.MARKETPLACE_URL}/item/${type2}/${data}`)).json();
|
||||
} catch (e) {
|
||||
return toast(this.props.toastLanguage.error);
|
||||
}
|
||||
|
||||
this.setState({
|
||||
current_data: { type: type2, name: data, content: info },
|
||||
@@ -64,14 +72,22 @@ export default class Marketplace extends React.PureComponent {
|
||||
});
|
||||
|
||||
let button = this.buttons.install;
|
||||
|
||||
const installed = JSON.parse(localStorage.getItem('installed'));
|
||||
if (installed.some(item => item.name === data)) button = this.buttons.uninstall;
|
||||
this.setState({ button: button });
|
||||
|
||||
if (installed.some(item => item.name === data)) {
|
||||
button = this.buttons.uninstall;
|
||||
}
|
||||
|
||||
this.setState({
|
||||
button: button
|
||||
});
|
||||
|
||||
document.getElementById('marketplace').style.display = 'none';
|
||||
document.getElementById('seemore').style.display = 'none';
|
||||
document.getElementById('item').style.display = 'block';
|
||||
break;
|
||||
|
||||
default:
|
||||
document.getElementById('marketplace').style.display = 'block';
|
||||
document.getElementById('item').style.display = 'none';
|
||||
@@ -83,6 +99,7 @@ export default class Marketplace extends React.PureComponent {
|
||||
async getItems() {
|
||||
const data = await (await fetch(Constants.MARKETPLACE_URL + '/all')).json();
|
||||
const featured = await (await fetch(Constants.MARKETPLACE_URL + '/featured')).json();
|
||||
|
||||
this.setState({
|
||||
settings: data.data.settings,
|
||||
photo_packs: data.data.photo_packs,
|
||||
@@ -95,10 +112,16 @@ export default class Marketplace extends React.PureComponent {
|
||||
|
||||
manage(type) {
|
||||
switch (type) {
|
||||
case 'install': MarketplaceFunctions.install(this.state.current_data.type, this.state.current_data.content.data); break;
|
||||
case 'uninstall': MarketplaceFunctions.uninstall(this.state.current_data.content.data.name, this.state.current_data.type); break;
|
||||
default: break;
|
||||
case 'install':
|
||||
MarketplaceFunctions.install(this.state.current_data.type, this.state.current_data.content.data);
|
||||
break;
|
||||
case 'uninstall':
|
||||
MarketplaceFunctions.uninstall(this.state.current_data.content.data.name, this.state.current_data.type);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
toast(this.props.toastLanguage[type + 'ed']);
|
||||
this.setState({
|
||||
button: (type === 'install') ? this.buttons.uninstall : this.buttons.install
|
||||
@@ -106,8 +129,14 @@ export default class Marketplace extends React.PureComponent {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('animations') === 'true') document.getElementById('marketplace').classList.add('marketplaceanimation');
|
||||
if (navigator.onLine === false) return;
|
||||
if (localStorage.getItem('animations') === 'true') {
|
||||
document.getElementById('marketplace').classList.add('marketplaceanimation');
|
||||
}
|
||||
|
||||
if (navigator.onLine === false) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.getItems();
|
||||
}
|
||||
|
||||
|
||||
@@ -24,13 +24,19 @@ export default class Settings extends React.PureComponent {
|
||||
|
||||
if (document.getElementById('modal').classList.contains('dark')) { // Dark theme support for dropdowns
|
||||
const choices = document.getElementsByClassName('choices');
|
||||
for (let i = 0; i < choices.length; i++) choices[i].style.backgroundColor = '#2f3542';
|
||||
for (let i = 0; i < choices.length; i++) {
|
||||
choices[i].style.backgroundColor = '#2f3542';
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
settingsImport(e) {
|
||||
const content = JSON.parse(e.target.result);
|
||||
for (const key of Object.keys(content)) localStorage.setItem(key, content[key]);
|
||||
|
||||
for (const key of Object.keys(content)) {
|
||||
localStorage.setItem(key, content[key]);
|
||||
}
|
||||
|
||||
toast(this.props.toastLanguage.imported);
|
||||
}
|
||||
|
||||
|
||||
@@ -10,15 +10,20 @@ import Date from './time/Date';
|
||||
|
||||
export default class Widgets extends React.PureComponent {
|
||||
enabled(key) {
|
||||
const old = localStorage.getItem(key);
|
||||
let val = true;
|
||||
const stringValue = localStorage.getItem(key);
|
||||
let enabled = true;
|
||||
|
||||
if (old !== null) {
|
||||
if (old === 'true') val = true;
|
||||
if (old === 'false') val = false;
|
||||
if (stringValue !== null) {
|
||||
if (stringValue === 'true') {
|
||||
enabled = true;
|
||||
}
|
||||
|
||||
if (stringValue === 'false') {
|
||||
enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
return val;
|
||||
return enabled;
|
||||
}
|
||||
|
||||
// Render all the components
|
||||
@@ -30,7 +35,7 @@ export default class Widgets extends React.PureComponent {
|
||||
<React.Fragment>
|
||||
{enabled('searchBar') ? <Search language={language.search} /> : null}
|
||||
{enabled('greeting') ? <Greeting language={language.greeting} /> : null}
|
||||
{enabled('clock') ? <Clock/> : null}
|
||||
{enabled('time') ? <Clock/> : null}
|
||||
{enabled('date') ? <Date/> : null}
|
||||
{enabled('quote') ? <Quote language={language.toasts} languagecode={languagecode} /> : null}
|
||||
{enabled('view') ? <Maximise/> : null}
|
||||
|
||||
@@ -27,33 +27,46 @@ export default class Background extends React.PureComponent {
|
||||
localStorage.setItem('customBackgroundColour', JSON.stringify(gradientSettings));
|
||||
}
|
||||
}
|
||||
|
||||
const background = typeof gradientSettings === 'object' && gradientSettings !== null ? this.gradientStyleBuilder(gradientSettings) : `background-image: url(${url})`;
|
||||
|
||||
// Brightness
|
||||
let brightness = localStorage.getItem('brightness');
|
||||
if (localStorage.getItem('brightnessTime') && new Date().getHours() > 18) brightness = 75;
|
||||
if (localStorage.getItem('brightnessTime') && new Date().getHours() > 18) {
|
||||
brightness = 75;
|
||||
}
|
||||
|
||||
document.querySelector('#backgroundImage').setAttribute(
|
||||
'style',
|
||||
`${background}; -webkit-filter: blur(${localStorage.getItem('blur')}px) brightness(${brightness}%);`
|
||||
);
|
||||
|
||||
if (credit === 'false' && document.querySelector('#credits')) document.querySelector('#credits').style.display = 'none'; // Hide the credit
|
||||
if (credit === 'false' && document.querySelector('#credits')) {
|
||||
document.querySelector('#credits').style.display = 'none'; // Hide the credit
|
||||
}
|
||||
}
|
||||
|
||||
setCredit(photographer, unsplash, url) {
|
||||
let credit = photographer;
|
||||
if (unsplash) credit = `<a href='${url}' class='creditlink'>${photographer}</a> on <a href='https://unsplash.com/?utm_source=mue&utm_medium=referral' class='creditlink'>Unsplash</a>`;
|
||||
document.querySelector('#photographer').insertAdjacentHTML("beforeend", ` ${credit}`); // Append credit
|
||||
if (unsplash){
|
||||
credit = `<a href='${url}' class='creditlink'>${photographer}</a> on <a href='https://unsplash.com/?utm_source=mue&utm_medium=referral' class='creditlink'>Unsplash</a>`;
|
||||
}
|
||||
|
||||
document.querySelector('#photographer').insertAdjacentHTML('beforeend', ` ${credit}`); // Append credit
|
||||
document.getElementById('credit').textContent = credit;
|
||||
document.getElementById('photographerCard').textContent = credit;
|
||||
}
|
||||
|
||||
doOffline() { // Handles setting the background if the user is offline
|
||||
const offlineImages = require('./offline_images.json');
|
||||
|
||||
const photographers = Object.keys(offlineImages); // Get all photographers from the keys in offlineImages.json
|
||||
const photographer = photographers[Math.floor(Math.random() * photographers.length)]; // Select a random photographer from the keys
|
||||
|
||||
const randomImage = offlineImages[photographer].photo[
|
||||
Math.floor(Math.random() * offlineImages[photographer].photo.length)
|
||||
]; // Select a random image
|
||||
|
||||
const url = `../offline-images/${randomImage}.jpg`;
|
||||
|
||||
this.setBackground(url);
|
||||
@@ -66,38 +79,54 @@ export default class Background extends React.PureComponent {
|
||||
const offlineMode = localStorage.getItem('offlineMode');
|
||||
|
||||
const photoPack = JSON.parse(localStorage.getItem('photo_packs'));
|
||||
|
||||
const customBackgroundColour = localStorage.getItem('customBackgroundColour');
|
||||
const customBackground = localStorage.getItem('customBackground');
|
||||
|
||||
const favourited = JSON.parse(localStorage.getItem('favourite'));
|
||||
|
||||
if (favourited) {
|
||||
if (offlineMode === 'true') return this.doOffline();
|
||||
if (offlineMode === 'true') {
|
||||
return this.doOffline();
|
||||
}
|
||||
|
||||
this.setBackground(favourited.url, null, 'true');
|
||||
this.setCredit(favourited.credit);
|
||||
document.getElementById('location').textContent = favourited.location;
|
||||
} else if (photoPack) {
|
||||
if (offlineMode === 'true') return this.doOffline();
|
||||
if (offlineMode === 'true') {
|
||||
return this.doOffline();
|
||||
}
|
||||
|
||||
const randomPhoto = photoPack[Math.floor(Math.random() * photoPack.length)];
|
||||
|
||||
this.setBackground(randomPhoto.url.default, null, randomPhoto.photographer);
|
||||
this.setCredit(randomPhoto.photographer);
|
||||
document.getElementById('location').textContent = randomPhoto.location;
|
||||
}
|
||||
else if (customBackgroundColour) this.setBackground(null, customBackgroundColour, 'false');
|
||||
else if (customBackground !== '') {
|
||||
} else if (customBackgroundColour) {
|
||||
this.setBackground(null, customBackgroundColour, 'false');
|
||||
} else if (customBackground !== '') {
|
||||
if (customBackground.includes('.mp4') || customBackground.includes('.webm') || customBackground.includes('.ogg')) {
|
||||
document.getElementById('backgroundImage').innerHTML = `
|
||||
<video autoplay muted loop id='backgroundVideo'>
|
||||
<source src='${customBackground}'/>
|
||||
</video>`;
|
||||
} else this.setBackground(customBackground, null, 'false'); // Local
|
||||
} else {
|
||||
this.setBackground(customBackground, null, 'false'); // Local
|
||||
}
|
||||
} else { // Online
|
||||
if (offlineMode === 'true') return this.doOffline();
|
||||
if (offlineMode === 'true') {
|
||||
return this.doOffline();
|
||||
}
|
||||
|
||||
try { // First we try and get an image from the API...
|
||||
const enabled = localStorage.getItem('webp');
|
||||
let requestURL;
|
||||
|
||||
switch (localStorage.getItem('backgroundAPI')) {
|
||||
case 'unsplash': requestURL = `${Constants.UNSPLASH_URL}/getImage`; break;
|
||||
case 'unsplash':
|
||||
requestURL = `${Constants.UNSPLASH_URL}/getImage`;
|
||||
break;
|
||||
default: // Defaults to Mue
|
||||
if (localStorage.getItem('supportswebp') === 'true' && enabled === 'true') requestURL = `${Constants.API_URL}/getImage?webp=true`;
|
||||
else requestURL = `${Constants.API_URL}/getImage?category=Outdoors`;
|
||||
@@ -106,16 +135,24 @@ export default class Background extends React.PureComponent {
|
||||
|
||||
const data = await (await fetch(requestURL)).json(); // Fetch JSON data from requestURL
|
||||
|
||||
if (data.statusCode === 429) this.doOffline(); // If we hit the rate limit, fallback to local images
|
||||
else { // Otherwise, set the background and credit from remote data
|
||||
if (data.statusCode === 429) {
|
||||
this.doOffline(); // If we hit the rate limit, fallback to local images
|
||||
} else { // Otherwise, set the background and credit from remote data
|
||||
this.setBackground(data.file);
|
||||
if (localStorage.getItem('backgroundAPI') === 'unsplash') return this.setCredit(data.photographer, 'unsplash', data.photographer_page);
|
||||
|
||||
if (localStorage.getItem('backgroundAPI') === 'unsplash') {
|
||||
return this.setCredit(data.photographer, 'unsplash', data.photographer_page);
|
||||
}
|
||||
|
||||
this.setCredit(data.photographer);
|
||||
document.getElementById('camera').textContent = data.camera || 'N/A';
|
||||
document.getElementById('resolution').textContent = data.resolution || 'N/A';
|
||||
}
|
||||
|
||||
if (data.location.replace(/[null]+/g, '') === ' ') return document.querySelector('#backgroundCredits').style.display = 'none';
|
||||
if (data.location.replace(/[null]+/g, '') === ' ') {
|
||||
return document.querySelector('#backgroundCredits').style.display = 'none';
|
||||
}
|
||||
|
||||
document.getElementById('location').innerText = `${data.location.replace('null', '')}`; // Set the location tooltip
|
||||
} catch (e) { // ..and if that fails we load one locally
|
||||
this.doOffline();
|
||||
@@ -124,8 +161,14 @@ export default class Background extends React.PureComponent {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('background') === 'false') return document.querySelector('#credits').style.display = 'none'; // Hide the credit
|
||||
if (localStorage.getItem('animations') === 'true') document.querySelector('#backgroundImage').classList.add('fade-in');
|
||||
if (localStorage.getItem('background') === 'false') {
|
||||
return document.querySelector('#credits').style.display = 'none'; // Hide the credit
|
||||
}
|
||||
|
||||
if (localStorage.getItem('animations') === 'true') {
|
||||
document.querySelector('#backgroundImage').classList.add('fade-in');
|
||||
}
|
||||
|
||||
this.determineMode();
|
||||
}
|
||||
|
||||
|
||||
@@ -20,18 +20,26 @@ export default class Favourite extends React.PureComponent {
|
||||
const location = document.getElementById('location').textContent;
|
||||
|
||||
localStorage.setItem('favourite', JSON.stringify({ url: url, credit: credit, location: location }));
|
||||
this.setState({ favourited: <StarIcon onClick={() => this.favourite()} /> });
|
||||
|
||||
this.setState({
|
||||
favourited: <StarIcon onClick={() => this.favourite()} />
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('favourite')) {
|
||||
this.setState({ favourited: <StarIcon onClick={() => this.favourite()} /> });
|
||||
this.setState({
|
||||
favourited: <StarIcon onClick={() => this.favourite()} />
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
if (localStorage.getItem('favouriteEnabled') === 'false' || localStorage.getItem('background') === 'false' || localStorage.getItem('customBackgroundColour') || localStorage.getItem('customBackground')) return null;
|
||||
if (localStorage.getItem('favouriteEnabled') === 'false' || localStorage.getItem('background') === 'false' || localStorage.getItem('customBackgroundColour') || localStorage.getItem('customBackground')) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return <div className='favourite'>
|
||||
{this.state.favourited}
|
||||
</div>
|
||||
|
||||
@@ -27,16 +27,23 @@ export default class View extends React.PureComponent {
|
||||
});
|
||||
|
||||
if (this.state.hidden === false) {
|
||||
this.setState({ hidden: true });
|
||||
this.setState({
|
||||
hidden: true
|
||||
});
|
||||
this.setAttribute(0, 100);
|
||||
} else {
|
||||
this.setState({ hidden: false });
|
||||
this.setState({
|
||||
hidden: false
|
||||
});
|
||||
this.setAttribute(localStorage.getItem('blur'), localStorage.getItem('brightness'));
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
if (localStorage.getItem('background') === 'false') return null;
|
||||
if (localStorage.getItem('background') === 'false') {
|
||||
return null;
|
||||
}
|
||||
|
||||
return <div className='view'>
|
||||
<FullscreenIcon onClick={() => this.viewStuff()} />
|
||||
</div>
|
||||
|
||||
@@ -11,15 +11,21 @@ export default class Greeting extends React.PureComponent {
|
||||
}
|
||||
|
||||
doEvents(time, message) {
|
||||
if (localStorage.getItem('events') === 'false') return message;
|
||||
if (localStorage.getItem('events') === 'false') {
|
||||
return message;
|
||||
}
|
||||
|
||||
// Get current month & day
|
||||
const m = time.getMonth();
|
||||
const d = time.getDate();
|
||||
|
||||
if (m === 11 && d === 25) message = this.props.language.christmas; // If it's December 25th, set the greeting string to "Merry Christmas"
|
||||
else if (m === 0 && d === 1) message = this.props.language.newyear; // If the date is January 1st, set the greeting string to "Happy new year"
|
||||
else if (m === 9 && d === 31) message = this.props.language.halloween; // If it's October 31st, set the greeting string to "Happy Halloween"
|
||||
if (m === 11 && d === 25) {
|
||||
message = this.props.language.christmas; // If it's December 25th, set the greeting string to "Merry Christmas"
|
||||
} else if (m === 0 && d === 1) {
|
||||
message = this.props.language.newyear; // If the date is January 1st, set the greeting string to "Happy new year"
|
||||
} else if (m === 9 && d === 31) {
|
||||
message = this.props.language.halloween; // If it's October 31st, set the greeting string to "Happy Halloween"
|
||||
}
|
||||
|
||||
return message;
|
||||
}
|
||||
@@ -29,13 +35,19 @@ export default class Greeting extends React.PureComponent {
|
||||
const hour = now.getHours();
|
||||
|
||||
let message = this.props.language.evening; // Set the default greeting string to "Good evening"
|
||||
if (hour < 12) message = this.props.language.morning; // If it's before 12am, set the greeting string to "Good morning"
|
||||
else if (hour < 18) message = this.props.language.afternoon; // If it's before 6pm, set the greeting string to "Good afternoon"
|
||||
if (hour < 12) {
|
||||
message = this.props.language.morning; // If it's before 12am, set the greeting string to "Good morning"
|
||||
} else if (hour < 18) {
|
||||
message = this.props.language.afternoon; // If it's before 6pm, set the greeting string to "Good afternoon"
|
||||
}
|
||||
|
||||
// Events
|
||||
message = this.doEvents(now, message);
|
||||
|
||||
const custom = localStorage.getItem('defaultGreetingMessage');
|
||||
if (custom === 'false') message = '';
|
||||
if (custom === 'false') {
|
||||
message = '';
|
||||
}
|
||||
|
||||
// Name
|
||||
let name = '';
|
||||
@@ -45,14 +57,20 @@ export default class Greeting extends React.PureComponent {
|
||||
if (data.replace(/\s/g, '').length > 0) name = `, ${data.trim()}`;
|
||||
}
|
||||
|
||||
if (custom === 'false') name = name.replace(',', '');
|
||||
if (custom === 'false') {
|
||||
name = name.replace(',', '');
|
||||
}
|
||||
|
||||
// Birthday
|
||||
const birth = new Date(localStorage.getItem('birthday'));
|
||||
if (localStorage.getItem('birthdayenabled') === 'true' && birth.getDate() === now.getDate() && birth.getMonth() === now.getMonth()) message = 'Happy Birthday';
|
||||
if (localStorage.getItem('birthdayenabled') === 'true' && birth.getDate() === now.getDate() && birth.getMonth() === now.getMonth()) {
|
||||
message = 'Happy Birthday';
|
||||
}
|
||||
|
||||
// Set the state to the greeting string
|
||||
this.setState({ greeting: `${message}${name}` });
|
||||
this.setState({
|
||||
greeting: `${message}${name}`
|
||||
});
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
|
||||
@@ -23,7 +23,9 @@ export default class Navbar extends React.PureComponent {
|
||||
</Tooltip>
|
||||
);
|
||||
|
||||
if (localStorage.getItem('refresh') === 'false') refreshHTML = null;
|
||||
if (localStorage.getItem('refresh') === 'false') {
|
||||
refreshHTML = null;
|
||||
}
|
||||
|
||||
// toggle feedback button
|
||||
let feedbackHTML = (
|
||||
@@ -32,7 +34,9 @@ export default class Navbar extends React.PureComponent {
|
||||
</Tooltip>
|
||||
);
|
||||
|
||||
if (Constants.BETA_VERSION === false) feedbackHTML = null;
|
||||
if (Constants.BETA_VERSION === false){
|
||||
feedbackHTML = null;
|
||||
}
|
||||
|
||||
return (
|
||||
<div className='navbar-container'>
|
||||
|
||||
@@ -30,7 +30,9 @@ export default class Notes extends React.PureComponent {
|
||||
|
||||
render() {
|
||||
let classList = 'notescontainer';
|
||||
if (localStorage.getItem('darkTheme') === 'true') classList += ' dark';
|
||||
if (localStorage.getItem('darkTheme') === 'true') {
|
||||
classList += ' dark';
|
||||
}
|
||||
|
||||
return (
|
||||
<span id='noteContainer' className={classList}>
|
||||
|
||||
@@ -16,7 +16,9 @@ export default class Quote extends React.PureComponent {
|
||||
this.state = {
|
||||
quote: '',
|
||||
author: '',
|
||||
favourited: <StarIcon2 className='copyButton' onClick={() => this.favourite()} />
|
||||
favourited: <StarIcon2 className='copyButton' onClick={() => this.favourite()} />,
|
||||
tweet: <TwitterIcon className='copyButton' onClick={() => this.tweetQuote()} />,
|
||||
copy: <FileCopy className='copyButton' onClick={() => this.copyQuote()} />
|
||||
};
|
||||
}
|
||||
|
||||
@@ -30,7 +32,11 @@ export default class Quote extends React.PureComponent {
|
||||
|
||||
getQuotePack() {
|
||||
let quotePack = localStorage.getItem('quote_packs');
|
||||
if (quotePack === 'undefined') return this.doOffline();
|
||||
|
||||
if (quotePack === 'undefined') {
|
||||
return this.doOffline();
|
||||
}
|
||||
|
||||
quotePack = JSON.parse(quotePack);
|
||||
|
||||
if (quotePack) {
|
||||
@@ -39,7 +45,9 @@ export default class Quote extends React.PureComponent {
|
||||
quote: '"' + data.quote + '"',
|
||||
author: data.author
|
||||
});
|
||||
} else this.doOffline();
|
||||
} else {
|
||||
this.doOffline();
|
||||
}
|
||||
}
|
||||
|
||||
async getQuote() {
|
||||
@@ -57,16 +65,24 @@ export default class Quote extends React.PureComponent {
|
||||
}
|
||||
|
||||
const favouriteQuote = localStorage.getItem('favouriteQuote');
|
||||
if (favouriteQuote) return this.setState({
|
||||
quote: favouriteQuote.split(' - ')[0],
|
||||
author: favouriteQuote.split(' - ')[1]
|
||||
});
|
||||
if (favouriteQuote) {
|
||||
return this.setState({
|
||||
quote: favouriteQuote.split(' - ')[0],
|
||||
author: favouriteQuote.split(' - ')[1]
|
||||
});
|
||||
}
|
||||
|
||||
if (localStorage.getItem('offlineMode') === 'true') return this.doOffline();
|
||||
if (localStorage.getItem('offlineMode') === 'true') {
|
||||
return this.doOffline();
|
||||
}
|
||||
|
||||
try { // First we try and get a quote from the API...
|
||||
const data = await (await fetch(Constants.API_URL + '/getQuote?language=' + localStorage.getItem('quotelanguage'))).json();
|
||||
if (data.statusCode === 429) return this.doOffline(); // If we hit the ratelimit, we fallback to local quotes
|
||||
|
||||
if (data.statusCode === 429) {
|
||||
return this.doOffline(); // If we hit the ratelimit, we fallback to local quotes
|
||||
}
|
||||
|
||||
this.setState({
|
||||
quote: '"' + data.quote + '"',
|
||||
author: data.author,
|
||||
@@ -82,34 +98,50 @@ export default class Quote extends React.PureComponent {
|
||||
toast(this.props.language.quote);
|
||||
}
|
||||
|
||||
tweetQuote() {
|
||||
window.open(`https://twitter.com/intent/tweet?text=${this.state.quote} - ${this.state.author} on @getmue`, '_blank').focus();
|
||||
}
|
||||
|
||||
favourite() {
|
||||
if (localStorage.getItem('favouriteQuote')) {
|
||||
localStorage.removeItem('favouriteQuote');
|
||||
this.setState({ favourited: <StarIcon2 className='copyButton' onClick={() => this.favourite()} /> });
|
||||
this.setState({
|
||||
favourited: <StarIcon2 className='copyButton' onClick={() => this.favourite()} />
|
||||
});
|
||||
} else {
|
||||
localStorage.setItem('favouriteQuote', this.state.quote + ' - ' + this.state.author);
|
||||
this.setState({ favourited: <StarIcon className='copyButton' onClick={() => this.favourite()} /> });
|
||||
this.setState({
|
||||
favourited: <StarIcon className='copyButton' onClick={() => this.favourite()} />
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('favouriteQuote')) this.setState({ favourited: <StarIcon className='copyButton' onClick={() => this.favourite()} /> });
|
||||
if (localStorage.getItem('favouriteQuoteEnabled') === 'false') this.setState({ favourited: null });
|
||||
if (localStorage.getItem('favouriteQuote')) {
|
||||
this.setState({ favourited: <StarIcon className='copyButton' onClick={() => this.favourite()} /> });
|
||||
}
|
||||
|
||||
if (localStorage.getItem('favouriteQuoteEnabled') === 'false') {
|
||||
this.setState({ favourited: null });
|
||||
}
|
||||
|
||||
if (localStorage.getItem('copyButton') === 'false') {
|
||||
this.setState({ copy: null });
|
||||
}
|
||||
|
||||
if (localStorage.getItem('tweetEnabled') === 'false') {
|
||||
this.setState({ tweet: null });
|
||||
}
|
||||
|
||||
this.getQuote();
|
||||
}
|
||||
|
||||
render() {
|
||||
let copy = <FileCopy className='copyButton' onClick={() => this.copyQuote()}></FileCopy>;
|
||||
if (localStorage.getItem('copyButton') === 'false') copy = null;
|
||||
|
||||
let tweet = <TwitterIcon className='copyButton' onClick={() => window.open(`https://twitter.com/intent/tweet?text=${this.state.quote} - ${this.state.author} on @getmue`, '_blank').focus()}/>
|
||||
if (localStorage.getItem('tweetButton') === 'false') tweet = null;
|
||||
|
||||
return (
|
||||
<div className='quotediv'>
|
||||
<h1 className='quote'>{`${this.state.quote}`}</h1>
|
||||
<h1 className='quoteauthor'>
|
||||
<a href={this.state.authorlink} className='quoteauthorlink' target='_blank' rel='noopener noreferrer'>{this.state.author}</a> {copy} {tweet} {this.state.favourited}
|
||||
<a href={this.state.authorlink} className='quoteauthorlink' target='_blank' rel='noopener noreferrer'>{this.state.author}</a> {this.state.copy} {this.state.tweet} {this.state.favourited}
|
||||
</h1>
|
||||
</div>
|
||||
);
|
||||
|
||||
@@ -20,7 +20,11 @@ export default class Search extends React.PureComponent {
|
||||
voiceSearch.start();
|
||||
const searchText = document.getElementById('searchtext');
|
||||
voiceSearch.onresult = (event) => searchText.value = event.results[0][0].transcript;
|
||||
voiceSearch.onend = () => setTimeout(() => window.location.href = this.state.url + `?${this.state.query}=` + searchText.value, 1000);
|
||||
voiceSearch.onend = () =>{
|
||||
setTimeout(() => {
|
||||
window.location.href = this.state.url + `?${this.state.query}=` + searchText.value;
|
||||
}, 1000);
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
|
||||
@@ -19,39 +19,56 @@ export default class Clock extends React.PureComponent {
|
||||
const now = new Date();
|
||||
|
||||
// Percentage
|
||||
if (localStorage.getItem('percentageComplete') === 'true') return this.setState({ time: (now.getHours() / 24).toFixed(2).replace('0.', '') + '%'});
|
||||
if (localStorage.getItem('percentageComplete') === 'true') {
|
||||
return this.setState({ time: (now.getHours() / 24).toFixed(2).replace('0.', '') + '%'});
|
||||
}
|
||||
|
||||
// Analog clock
|
||||
if (localStorage.getItem('analog') === 'true') {
|
||||
require('react-clock/dist/Clock.css');
|
||||
this.setState({ time: now });
|
||||
require('react-clock/dist/Clock.css'); // load analog clock css
|
||||
this.setState({
|
||||
time: now
|
||||
});
|
||||
} else {
|
||||
// Default clock
|
||||
let time, sec = '';
|
||||
|
||||
// Extra 0
|
||||
const zero = localStorage.getItem('zero');
|
||||
|
||||
if (localStorage.getItem('seconds') === 'true') {
|
||||
if (zero === 'false') sec = `:${now.getSeconds()}`;
|
||||
else sec = `:${('00' + now.getSeconds()).slice(-2)}`;
|
||||
if (zero === 'false') {
|
||||
sec = ':' + now.getSeconds();
|
||||
} else {
|
||||
sec = `:${('00' + now.getSeconds()).slice(-2)}`;
|
||||
}
|
||||
}
|
||||
|
||||
if (localStorage.getItem('24hour') === 'true') {
|
||||
if (zero === 'false') time = `${now.getHours()}:${now.getMinutes()}${sec}`;
|
||||
else time = `${('00' + now.getHours()).slice(-2)}:${('00' + now.getMinutes()).slice(-2)}${sec}`;
|
||||
if (zero === 'false') {
|
||||
time = `${now.getHours()}:${now.getMinutes()}${sec}`;
|
||||
} else {
|
||||
time = `${('00' + now.getHours()).slice(-2)}:${('00' + now.getMinutes()).slice(-2)}${sec}`;
|
||||
}
|
||||
|
||||
this.setState({ time: time });
|
||||
} else {
|
||||
// 12 hour support
|
||||
let hours = now.getHours();
|
||||
if (hours > 12) hours -= 12;
|
||||
|
||||
if (hours > 12) {
|
||||
hours -= 12;
|
||||
}
|
||||
|
||||
// Toggle AM/PM
|
||||
let ampm = now.getHours() > 11 ? 'PM' : 'AM';
|
||||
if (localStorage.getItem('ampm') === 'false') ampm = '';
|
||||
if (localStorage.getItem('ampm') === 'false') {
|
||||
ampm = '';
|
||||
}
|
||||
|
||||
if (zero === 'false') time = `${hours}:${now.getMinutes()}${sec}`;
|
||||
else time = `${('00' + hours).slice(-2)}:${('00' + now.getMinutes()).slice(-2)}${sec}`;
|
||||
if (zero === 'false') {
|
||||
time = `${hours}:${now.getMinutes()}${sec}`;
|
||||
} else {
|
||||
time = `${('00' + hours).slice(-2)}:${('00' + now.getMinutes()).slice(-2)}${sec}`;
|
||||
}
|
||||
|
||||
this.setState({
|
||||
time: time,
|
||||
@@ -65,15 +82,15 @@ export default class Clock extends React.PureComponent {
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
if (localStorage.getItem('time') === 'false') return;
|
||||
this.startTime(0);
|
||||
}
|
||||
|
||||
render() {
|
||||
if (localStorage.getItem('time') === 'false') return null;
|
||||
|
||||
let clockHTML = <h1 className='clock'>{this.state.time}<span className='ampm'>{this.state.ampm}</span> </h1>;
|
||||
if (localStorage.getItem('analog') === 'true') clockHTML = <Analog className='analogclock' value={this.state.time} renderHourMarks={false} renderMinuteMarks={false} />;
|
||||
let clockHTML = <h1 className='clock'>{this.state.time}<span className='ampm'>{this.state.ampm}</span></h1>;
|
||||
|
||||
if (localStorage.getItem('analog') === 'true') {
|
||||
clockHTML = <Analog className='analogclock' value={this.state.time} renderHourMarks={false} renderMinuteMarks={false} />;
|
||||
}
|
||||
|
||||
return clockHTML;
|
||||
}
|
||||
|
||||
@@ -5,24 +5,24 @@ export default class DateWidget extends React.PureComponent {
|
||||
constructor(...args) {
|
||||
super(...args);
|
||||
this.state = {
|
||||
date: ''
|
||||
date: ''
|
||||
};
|
||||
}
|
||||
|
||||
getDate() {
|
||||
const date = new Date();
|
||||
|
||||
const short = localStorage.getItem('short');
|
||||
const dateFormat = localStorage.getItem('dateFormat');
|
||||
|
||||
if (short === 'true') {
|
||||
const dateDay = date.getDate();
|
||||
const dateMonth = date.getMonth() + 1;
|
||||
const dateYear = date.getFullYear();
|
||||
|
||||
let day = dateDay, month = dateMonth, year = dateYear;
|
||||
let day = dateDay;
|
||||
let month = dateMonth;
|
||||
let year = dateYear;
|
||||
|
||||
switch (dateFormat) {
|
||||
switch (localStorage.getItem('dateFormat')) {
|
||||
case 'MDY':
|
||||
day = dateMonth;
|
||||
month = dateDay;
|
||||
@@ -36,13 +36,21 @@ export default class DateWidget extends React.PureComponent {
|
||||
|
||||
let format;
|
||||
switch (localStorage.getItem('shortFormat')) {
|
||||
case 'dash': format = `${day}-${month}-${year}`; break;
|
||||
case 'gaps': format = `${day} - ${month} - ${year}`; break;
|
||||
default: format = `${day}/${month}/${year}`;
|
||||
case 'dash':
|
||||
format = `${day}-${month}-${year}`;
|
||||
break;
|
||||
case 'gaps':
|
||||
format = `${day} - ${month} - ${year}`;
|
||||
break;
|
||||
default:
|
||||
format = `${day}/${month}/${year}`;
|
||||
}
|
||||
|
||||
this.setState({ date: format });
|
||||
} else { // full date
|
||||
this.setState({
|
||||
date: format
|
||||
});
|
||||
} else {
|
||||
// Full date
|
||||
const lang = localStorage.getItem('language');
|
||||
|
||||
const day = date.toLocaleDateString(lang, { weekday: 'long' });
|
||||
@@ -50,7 +58,9 @@ export default class DateWidget extends React.PureComponent {
|
||||
const month = date.toLocaleDateString(lang, { month: 'long' });
|
||||
const year = date.getFullYear();
|
||||
|
||||
this.setState({ date: `${day} ${nth} ${month} ${year}` });
|
||||
this.setState({
|
||||
date: `${day} ${nth} ${month} ${year}`
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -9,8 +9,13 @@ export default function hexToRgb(value) {
|
||||
const valid = hexRegexp.test(value);
|
||||
|
||||
if (valid) {
|
||||
if (value[0] === '#') value = value.slice(1, value.length);
|
||||
if (value.length === 3) value = value.replace(regexp, '$1$1$2$2$3$3');
|
||||
if (value[0] === '#') {
|
||||
value = value.slice(1, value.length);
|
||||
}
|
||||
|
||||
if (value.length === 3){
|
||||
value = value.replace(regexp, '$1$1$2$2$3$3');
|
||||
}
|
||||
|
||||
const red = parseInt(value.substr(0, 2), 16);
|
||||
const green = parseInt(value.substr(2, 2), 16);
|
||||
|
||||
@@ -3,9 +3,17 @@ export default function rgbToHex(red, green, blue) {
|
||||
let g16 = green.toString(16);
|
||||
let b16 = blue.toString(16);
|
||||
|
||||
if (red < 16) r16 = `0${r16}`;
|
||||
if (green < 16) g16 = `0${g16}`;
|
||||
if (blue < 16) b16 = `0${b16}`;
|
||||
if (red < 16) {
|
||||
r16 = `0${r16}`;
|
||||
}
|
||||
|
||||
if (green < 16) {
|
||||
g16 = `0${g16}`;
|
||||
}
|
||||
|
||||
if (blue < 16) {
|
||||
b16 = `0${b16}`;
|
||||
}
|
||||
|
||||
return r16 + g16 + b16;
|
||||
}
|
||||
|
||||
@@ -18,11 +18,19 @@ export default function rgbToHSv({ red, green, blue }) {
|
||||
gg = diffc(gabs);
|
||||
bb = diffc(babs);
|
||||
|
||||
if (rabs === v) h = bb - gg;
|
||||
else if (gabs === v) h = (1 / 3) + rr - bb;
|
||||
else if (babs === v) h = (2 / 3) + gg - rr;
|
||||
if (h < 0) h += 1;
|
||||
else if (h > 1) h -= 1;
|
||||
if (rabs === v){
|
||||
h = bb - gg;
|
||||
} else if (gabs === v) {
|
||||
h = (1 / 3) + rr - bb;
|
||||
} else if (babs === v) {
|
||||
h = (2 / 3) + gg - rr;
|
||||
}
|
||||
|
||||
if (h < 0) {
|
||||
h += 1;
|
||||
} else if (h > 1) {
|
||||
h -= 1;
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
|
||||
@@ -10,8 +10,10 @@ export default function setRGBA(red, green, blue, alpha) {
|
||||
blue: blue | 0,
|
||||
};
|
||||
|
||||
if (isValidRGBValue(alpha) === true) color.alpha = alpha | 0;
|
||||
// RGBToHSL(color.r, color.g, color.b);
|
||||
if (isValidRGBValue(alpha) === true) {
|
||||
color.alpha = alpha | 0;
|
||||
}
|
||||
|
||||
return color;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,8 +18,9 @@ export default class MarketplaceFunctions {
|
||||
localStorage.removeItem('quoteAPI');
|
||||
break;
|
||||
default:
|
||||
try { localStorage.removeItem(type); }
|
||||
catch (e) {
|
||||
try {
|
||||
localStorage.removeItem(type);
|
||||
} catch (e) {
|
||||
toast('Failed to uninstall addon, check the console');
|
||||
console.error(e);
|
||||
}
|
||||
@@ -39,17 +40,32 @@ export default class MarketplaceFunctions {
|
||||
switch (type) {
|
||||
case 'settings':
|
||||
localStorage.removeItem('backup_settings');
|
||||
|
||||
let oldSettings = [];
|
||||
for (const key of Object.keys(localStorage)) oldSettings.push({ name: key, value: localStorage.getItem(key) });
|
||||
for (const key of Object.keys(localStorage)) {
|
||||
oldSettings.push({
|
||||
name: key,
|
||||
value: localStorage.getItem(key)
|
||||
});
|
||||
}
|
||||
|
||||
localStorage.setItem('backup_settings', JSON.stringify(oldSettings));
|
||||
input.settings.forEach(element => localStorage.setItem(element.name, element.value));
|
||||
break;
|
||||
case 'photo_packs': localStorage.setItem('photo_packs', JSON.stringify(input.photos)); break;
|
||||
|
||||
case 'photo_packs':
|
||||
localStorage.setItem('photo_packs', JSON.stringify(input.photos));
|
||||
break;
|
||||
|
||||
case 'quote_packs':
|
||||
if (input.quote_api) localStorage.setItem('quoteAPI', JSON.stringify(input.quote_api));
|
||||
if (input.quote_api) {
|
||||
localStorage.setItem('quoteAPI', JSON.stringify(input.quote_api));
|
||||
}
|
||||
|
||||
localStorage.setItem('quote_packs', JSON.stringify(input.quotes));
|
||||
break;
|
||||
default: break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
let installed = JSON.parse(localStorage.getItem('installed'));
|
||||
|
||||
@@ -18,7 +18,9 @@ const saveFile = (data, filename = 'file') => {
|
||||
export default class SettingsFunctions {
|
||||
static exportSettings() {
|
||||
let settings = {};
|
||||
for (const key of Object.keys(localStorage)) settings[key] = localStorage.getItem(key);
|
||||
for (const key of Object.keys(localStorage)) {
|
||||
settings[key] = localStorage.getItem(key);
|
||||
}
|
||||
saveFile(settings, 'mue-settings.json');
|
||||
}
|
||||
|
||||
@@ -27,8 +29,13 @@ export default class SettingsFunctions {
|
||||
let val = true;
|
||||
|
||||
if (old !== null && !value) {
|
||||
if (old === 'true') val = false;
|
||||
if (old === 'false') val = true;
|
||||
if (old === 'true') {
|
||||
val = false;
|
||||
}
|
||||
|
||||
if (old === 'false') {
|
||||
val = true;
|
||||
}
|
||||
}
|
||||
|
||||
localStorage.setItem(key, val);
|
||||
@@ -69,8 +76,11 @@ export default class SettingsFunctions {
|
||||
defaultSettings.forEach((element) => localStorage.setItem(element.name, element.value));
|
||||
|
||||
// Set theme depending on user preferred
|
||||
if (window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches) localStorage.setItem('darkTheme', true);
|
||||
else localStorage.setItem('darkTheme', false);
|
||||
if (window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches) {
|
||||
localStorage.setItem('darkTheme', true);
|
||||
} else {
|
||||
localStorage.setItem('darkTheme', false);
|
||||
}
|
||||
|
||||
// Languages
|
||||
const languages = ['nl', 'no', 'fr', 'ru', 'es'];
|
||||
@@ -79,9 +89,13 @@ export default class SettingsFunctions {
|
||||
if (languages.includes(browserLanguage)) {
|
||||
localStorage.setItem('language', browserLanguage);
|
||||
document.documentElement.lang = browserLanguage;
|
||||
} else localStorage.setItem('language', 'en');
|
||||
} else {
|
||||
localStorage.setItem('language', 'en');
|
||||
}
|
||||
|
||||
if (reset) localStorage.setItem('showWelcome', false);
|
||||
if (reset) {
|
||||
localStorage.setItem('showWelcome', false);
|
||||
}
|
||||
|
||||
// Finally we set this to true so it doesn't run the function on every load
|
||||
localStorage.setItem('firstRun', true);
|
||||
|
||||
Reference in New Issue
Block a user