diff --git a/src/features/greeting/Greeting.jsx b/src/features/greeting/Greeting.jsx index 3d75e700..d60bb64a 100644 --- a/src/features/greeting/Greeting.jsx +++ b/src/features/greeting/Greeting.jsx @@ -1,62 +1,57 @@ +import { useState, useEffect, useRef } from 'react'; import variables from 'config/variables'; -import { PureComponent, createRef } from 'react'; - import { nth, convertTimezone } from 'utils/date'; import EventBus from 'utils/eventbus'; - import './greeting.scss'; -const isEventsEnabled = localStorage.getItem('events') !== 'false'; -export default class Greeting extends PureComponent { - constructor() { - super(); - this.state = { - greeting: '', - }; - this.timer = undefined; - this.greeting = createRef(); - } - - /** - * Change the greeting message for the events of Christmas, New Year and Halloween. - * If the events setting is disabled, then the greeting message will not be changed. - * @param {Date} time The current time. - * @param {String} message The current greeting message. - * @returns The message variable is being returned. - */ - doEvents(time, message) { - if (!isEventsEnabled) { - return message; - } - - // Get current month & day - const month = time.getMonth(); - const date = time.getDate(); - - // Parse the customEvents from localStorage - const customEvents = JSON.parse(localStorage.getItem('customEvents') || '[]'); - - const event = customEvents.find((e) => e.month - 1 === month && e.date === date); - if (event) { - message = event.name; - } - +/** + * Change the greeting message for the events of Christmas, New Year and Halloween. + * If the events setting is disabled, then the greeting message will not be changed. + * @param {Date} time The current time. + * @param {String} message The current greeting message. + * @returns The message variable is being returned. + */ +const doEvents = (time, message) => { + const isEventsEnabled = localStorage.getItem('events') !== 'false'; + if (!isEventsEnabled) { return message; } - /** - * It takes a date object and returns the age of the person in years. - * @param {Date} date The date of birth. - * @returns The age of the person. - */ - calculateAge(date) { - const diff = Date.now() - date.getTime(); - const birthday = new Date(diff); - return Math.abs(birthday.getUTCFullYear() - 1970); + // Get current month & day + const month = time.getMonth(); + const date = time.getDate(); + + // Parse the customEvents from localStorage + const customEvents = JSON.parse(localStorage.getItem('customEvents') || '[]'); + + const event = customEvents.find((e) => e.month - 1 === month && e.date === date); + if (event) { + message = event.name; } - getGreeting(time = 60000 - (Date.now() % 60000)) { - this.timer = setTimeout(() => { + return message; +}; + +/** + * It takes a date object and returns the age of the person in years. + * @param {Date} date The date of birth. + * @returns The age of the person. + */ +const calculateAge = (date) => { + const diff = Date.now() - date.getTime(); + const birthday = new Date(diff); + return Math.abs(birthday.getUTCFullYear() - 1970); +}; + +const Greeting = () => { + const [greeting, setGreeting] = useState(''); + const [display, setDisplay] = useState('block'); + const [fontSize, setFontSize] = useState('1.6em'); + const greetingRef = useRef(); + const timerRef = useRef(null); + + const getGreeting = (time = 60000 - (Date.now() % 60000)) => { + timerRef.current = setTimeout(() => { let now = new Date(); const timezone = localStorage.getItem('timezone'); if (timezone && timezone !== 'auto') { @@ -83,7 +78,7 @@ export default class Greeting extends PureComponent { if (custom === 'false') { message = ''; } else { - message = this.doEvents(now, message); + message = doEvents(now, message); } // Name @@ -107,9 +102,9 @@ export default class Greeting extends PureComponent { const birth = new Date(localStorage.getItem('birthday')); if (birth.getDate() === now.getDate() && birth.getMonth() === now.getMonth()) { - if (localStorage.getItem('birthdayage') === 'true' && this.calculateAge(birth) !== 0) { + if (localStorage.getItem('birthdayage') === 'true' && calculateAge(birth) !== 0) { const text = variables.getMessage('widgets.greeting.birthday').split(' '); - message = `${text[0]} ${nth(this.calculateAge(birth))} ${text[1]}`; + message = `${text[0]} ${nth(calculateAge(birth))} ${text[1]}`; } else { message = variables.getMessage('widgets.greeting.birthday'); } @@ -117,49 +112,50 @@ export default class Greeting extends PureComponent { } // Set the state to the greeting string - this.setState({ - greeting: `${message}${name}`, - }); + setGreeting(`${message}${name}`); - this.getGreeting(); + getGreeting(); }, time); - } + }; - componentDidMount() { - EventBus.on('refresh', (data) => { + useEffect(() => { + const handleRefresh = (data) => { if (data === 'greeting' || data === 'timezone') { - if (localStorage.getItem('greeting') === 'false') { - return (this.greeting.current.style.display = 'none'); + const greetingSetting = localStorage.getItem('greeting'); + const zoomGreeting = localStorage.getItem('zoomGreeting'); + setDisplay(greetingSetting === 'false' ? 'none' : 'block'); + setFontSize(`${1.6 * Number((zoomGreeting || 100) / 100)}em`); + + if (greetingSetting !== 'false') { + if (timerRef.current) { + clearTimeout(timerRef.current); + } + getGreeting(0); } - - this.timer = null; - this.getGreeting(0); - - this.greeting.current.style.display = 'block'; - this.greeting.current.style.fontSize = `${ - 1.6 * Number((localStorage.getItem('zoomGreeting') || 100) / 100) - }em`; } - }); + }; // this comment can apply to all widget zoom features apart from the general one in the Accessibility section // in a nutshell: 1.6 is the current font size, and we do "localstorage || 100" so we don't have to try that 4.0 -> 5.0 thing again - this.greeting.current.style.fontSize = `${ - 1.6 * Number((localStorage.getItem('zoomGreeting') || 100) / 100) - }em`; + const zoomGreeting = localStorage.getItem('zoomGreeting'); + setFontSize(`${1.6 * Number((zoomGreeting || 100) / 100)}em`); - this.getGreeting(0); - } + getGreeting(0); - componentWillUnmount() { - EventBus.off('refresh'); - } + EventBus.on('refresh', handleRefresh); + return () => { + EventBus.off('refresh'); + if (timerRef.current) { + clearTimeout(timerRef.current); + } + }; + }, []); - render() { - return ( - - {this.state.greeting} - - ); - } -} + return ( + + {greeting} + + ); +}; + +export { Greeting as default, Greeting };