feat: add reverse timer

This commit is contained in:
MAZE 2024-08-31 19:39:31 +03:30
parent f3cea66847
commit 105f53ea02
8 changed files with 97 additions and 33 deletions

View file

@ -1,7 +1,7 @@
import { useEffect, useState, useRef, useMemo } from 'react'; import { useEffect, useState, useRef, useMemo } from 'react';
import { Modal } from '@/components/modal'; import { Modal } from '@/components/modal';
import { Timer } from '@/components/timer'; import { Timer } from './timer';
import { dispatch } from '@/lib/event'; import { dispatch } from '@/lib/event';
import { useSoundStore } from '@/stores/sound'; import { useSoundStore } from '@/stores/sound';
import { cn } from '@/helpers/styles'; import { cn } from '@/helpers/styles';
@ -63,7 +63,7 @@ export function SleepTimerModal({ onClose, show }: SleepTimerModalProps) {
useEffect(() => { useEffect(() => {
if (timeLeft === 0) { if (timeLeft === 0) {
setRunning(false); setRunning(false);
// pause();
dispatch(FADE_OUT, { duration: 1000 }); dispatch(FADE_OUT, { duration: 1000 });
setTimeSpent(0); setTimeSpent(0);
@ -107,7 +107,7 @@ export function SleepTimerModal({ onClose, show }: SleepTimerModalProps) {
)} )}
</div> </div>
{running ? <Timer displayHours={true} timer={timeLeft} /> : null} {running ? <Timer reverse={timeSpent} timer={timeLeft} /> : null}
<div className={styles.buttons}> <div className={styles.buttons}>
{running && ( {running && (

View file

@ -0,0 +1 @@
export { Reverse } from './reverse';

View file

@ -0,0 +1,30 @@
.reverse {
position: absolute;
top: 8px;
left: 8px;
padding: 4px 8px;
font-size: var(--font-2xsm);
color: var(--color-foreground-subtle);
background: linear-gradient(
var(--color-neutral-50),
var(--color-neutral-100)
);
border: 1px solid var(--color-neutral-200);
border-radius: 4px;
&::after {
position: absolute;
bottom: -1px;
left: 50%;
width: 75%;
height: 1px;
content: '';
background: linear-gradient(
90deg,
transparent,
var(--color-neutral-300),
transparent
);
transform: translateX(-50%);
}
}

View file

@ -0,0 +1,27 @@
import { padNumber } from '@/helpers/number';
import styles from './reverse.module.css';
interface ReverseProps {
time: number;
}
export function Reverse({ time }: ReverseProps) {
let hours = Math.floor(time / 3600);
let minutes = Math.floor((time % 3600) / 60);
let seconds = time % 60;
hours = isNaN(hours) ? 0 : hours;
minutes = isNaN(minutes) ? 0 : minutes;
seconds = isNaN(seconds) ? 0 : seconds;
const formattedHours = padNumber(hours);
const formattedMinutes = padNumber(minutes);
const formattedSeconds = padNumber(seconds);
return (
<div className={styles.reverse}>
- {formattedHours}:{formattedMinutes}:{formattedSeconds}
</div>
);
}

View file

@ -0,0 +1,29 @@
.timer {
position: relative;
display: flex;
align-items: center;
justify-content: center;
width: 100%;
padding: 48px 0;
font-size: var(--font-xlg);
font-weight: 500;
background-color: var(--color-neutral-50);
border: 1px solid var(--color-neutral-200);
border-radius: 12px;
&::after {
position: absolute;
bottom: -1px;
left: 50%;
width: 75%;
height: 1px;
content: '';
background: linear-gradient(
90deg,
transparent,
var(--color-neutral-400),
transparent
);
transform: translateX(-50%);
}
}

View file

@ -1,15 +1,15 @@
import { Reverse } from './reverse';
import { padNumber } from '@/helpers/number'; import { padNumber } from '@/helpers/number';
import { cn } from '@/helpers/styles';
import styles from './timer.module.css'; import styles from './timer.module.css';
interface TimerProps { interface TimerProps {
displayHours?: boolean; reverse: number;
tall?: boolean;
timer: number; timer: number;
} }
export function Timer({ displayHours = false, tall, timer }: TimerProps) { export function Timer({ reverse, timer }: TimerProps) {
let hours = Math.floor(timer / 3600); let hours = Math.floor(timer / 3600);
let minutes = Math.floor((timer % 3600) / 60); let minutes = Math.floor((timer % 3600) / 60);
let seconds = timer % 60; let seconds = timer % 60;
@ -23,16 +23,9 @@ export function Timer({ displayHours = false, tall, timer }: TimerProps) {
const formattedSeconds = padNumber(seconds); const formattedSeconds = padNumber(seconds);
return ( return (
<div className={cn(styles.timer, tall && styles.tall)}> <div className={styles.timer}>
{displayHours ? ( <Reverse time={reverse} />
<> {formattedHours}:{formattedMinutes}:{formattedSeconds}
{formattedHours}:{formattedMinutes}:{formattedSeconds}
</>
) : (
<>
{formattedMinutes}:{formattedSeconds}
</>
)}
</div> </div>
); );
} }

View file

@ -1,16 +0,0 @@
.timer {
display: flex;
align-items: center;
justify-content: center;
width: 100%;
padding: 30px 0;
font-size: var(--font-xlg);
font-weight: 500;
background-color: var(--color-neutral-50);
border: 1px solid var(--color-neutral-200);
border-radius: 8px;
&.tall {
padding: 60px 0;
}
}