123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135 |
- import './App.css';
- import { useEffect, useState } from 'react'
- const Timer = ({ timeInSeconds }) => {
- const [time, setTime] = useState(timeInSeconds)
- const [isPaused, setPaused] = useState(false)
- const hours = Math.floor(time / (60 * 60))
- const minutes = Math.floor((time % (60 * 60)) / 60)
- const seconds = Math.ceil((time % (60 * 60)) % 60)
- useEffect(() => {
- let interval = setInterval(() => {setTime(time => time - 1)}, 1000)
- if (time === 0 || isPaused) {
- clearInterval(interval)
- }
- return () => {clearInterval(interval)}
- }, [time, isPaused])
- useEffect(() => {
- setTime(timeInSeconds)
- }, [timeInSeconds])
- return (
- <>
- <div>{hours}:{minutes}:{seconds}</div>
- <button onClick={() => setPaused(!isPaused)}> астанавись/прадалжай </button>
- </>
- )
- }
- const TimerControl = ({setTimeCB}) => {
- const [hours, setHours] = useState('')
- const [minutes, setMinutes] = useState('')
- const [seconds, setSeconds] = useState('')
- const timeToSeconds = (hours, minutes, seconds) => {
- let time = (+hours * 60 * 60) + (+minutes * 60) + +seconds
- return time
- }
- const valuesDisappear = () => {
- setHours('')
- setMinutes('')
- setSeconds('')
- }
- return (
- <div>
- <input type="number" placeholder="hours" value={hours} onChange={(e) => setHours(e.target.value)}></input>
- <input type="number" placeholder="minutes" value={minutes} onChange={(e) => setMinutes(e.target.value)}></input>
- <input type="number" placeholder="seconds" value={seconds} onChange={(e) => setSeconds(e.target.value)}></input>
- <button onClick={() => {valuesDisappear(); setTimeCB(timeToSeconds(hours, minutes, seconds))}}>Start</button>
- </div>
- )
- }
- const TimerContainer = ({seconds, refresh, render: Render}) => {
- const [time, setTime] = useState(seconds)
- const [initialTime] = useState(performance.now())
- useEffect(() => {
- let interval = setInterval(() => {
- setTime(seconds - Math.floor((performance.now() - initialTime) / 1000))
- }, refresh)
- if (time <= 0) {
- setTime(0)
- clearInterval(interval)
- }
- return () => clearInterval(interval)
- }, [time, initialTime, refresh, seconds])
- useEffect(() => {
- setTime(seconds)
- }, [seconds])
- return (
- <Render seconds={time}/>
- )
- }
- const SecondsTimer = ({seconds}) => <h2>{seconds}</h2>
- const LCD = ({seconds: timeInSeconds}) => {
- const hours = Math.floor(timeInSeconds / (60 * 60))
- const minutes = Math.floor((timeInSeconds % (60 * 60)) / 60)
- const seconds = Math.ceil((timeInSeconds % (60 * 60)) % 60)
- return (
- <div>{hours}:{minutes}:{seconds}</div>
- )
- }
- const Watch = ({seconds: timeInSeconds}) => {
- const hours = Math.floor(timeInSeconds / (60 * 60))
- const minutes = Math.floor((timeInSeconds % (60 * 60)) / 60)
- const seconds = Math.ceil((timeInSeconds % (60 * 60)) % 60)
- const ratioH = 360 / 12 / 60 / 60
- const ratioM = 360 / 60 / 60
- const ratioS = 360 / 60
- const getAngle = (ratio, value) => (ratio * value)
- return (
- <>
- <div>{hours}:{minutes}:{seconds}</div>
- <div style={{position: 'relative'}}>
- <img src='http://draw.asmer.fe.a-level.com.ua/ClockFace/ClockFace.png' style={{position: 'absolute'}} />
- <img src='http://draw.asmer.fe.a-level.com.ua/ClockFace/ClockFace_H.png' style={{position: 'absolute', transform: `rotate(${getAngle(ratioH, timeInSeconds)}deg)`}}/>
- <img src='http://draw.asmer.fe.a-level.com.ua/ClockFace/ClockFace_M.png' style={{position: 'absolute', transform: `rotate(${getAngle(ratioM, timeInSeconds)}deg)`}}/>
- <img src='http://draw.asmer.fe.a-level.com.ua/ClockFace/ClockFace_S.png' style={{position: 'absolute', transform: `rotate(${getAngle(ratioS, timeInSeconds)}deg)`}} />
- </div>
- </>
- )
- }
- function App() {
- const [time, setTime] = useState(0)
- return (
- <div>
- <Timer timeInSeconds={time} />
- <TimerControl setTimeCB={seconds => setTime(seconds)}/>
- <TimerContainer seconds={1800} refresh={100} render={SecondsTimer}/>
- <TimerContainer seconds={5000} refresh={100} render={LCD}/>
- <TimerContainer seconds={time} refresh={100} render={Watch}/>
- </div>
- );
- }
- export default App;
|