230 lines
9.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"use client"
import type React from "react"
import { useState, useEffect } from "react"
import { useHistory } from "react-router-dom"
import BottomNavigation from "../components/BottomNavigation"
import HeaderNav from "../components/HeaderNav"
import video from "../assets/video.mov"
const Exercise: React.FC = () => {
const history = useHistory()
// const { id } = useParams<{ id: string }>()
const [isPlaying, setIsPlaying] = useState(false)
const [currentTime, setCurrentTime] = useState(0)
const [totalTime] = useState(900) // 15 minutes in seconds
const [currentSet, setCurrentSet] = useState(1)
const [totalSets] = useState(3)
useEffect(() => {
let interval: NodeJS.Timeout | undefined
if (isPlaying) {
interval = setInterval(() => {
setCurrentTime((prev) => {
if (prev >= totalTime) {
setIsPlaying(false)
// Show completion animation
history.push("/course-complete")
return totalTime
}
return prev + 1
})
}, 1000)
}
return () => {
if (interval) clearInterval(interval)
}
}, [isPlaying, totalTime, history])
const formatTime = (seconds: number) => {
const mins = Math.floor(seconds / 60)
const secs = seconds % 60
return `${mins.toString().padStart(2, "0")}:${secs.toString().padStart(2, "0")}`
}
const progress = (currentTime / totalTime) * 100
const PlayIcon = () => (
<svg className="w-10 h-10 text-white" fill="currentColor" viewBox="0 0 24 24">
<path d="M8 5v14l11-7z" />
</svg>
)
const PauseIcon = () => (
<svg className="w-10 h-10 text-white" fill="currentColor" viewBox="0 0 24 24">
<path d="M6 19h4V5H6v14zm8-14v14h4V5h-4z" />
</svg>
)
const RefreshIcon = () => (
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 24 24" fill="none" stroke="#6F6F6F" stroke-width="3" stroke-linecap="round" stroke-linejoin="round"> <path d="M2.5 2v6h6M21.5 22v-6h-6" /><path d="M22 11.5A10 10 0 0 0 3.2 7.2M2 12.5a10 10 0 0 0 18.8 4.2" /></svg>
)
const CheckIcon = () => (
<svg className="w-6 h-6 text-cyan-500" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={3} d="M5 13l4 4L19 7" />
</svg>
)
const exerciseSteps = [
{
title: "Исходное положение",
description:
"Лягте на спирку на коврик. Руки вдоль тела, ладони прижаты к полу. Ноги выпрямлены, носки направлены вверх. Поясница плотно прижата к полу.",
},
{
title: "Задание",
description:
"Медленно поднимите прямые ноги до угла 90 градусов. Задержитесь на 2 секунды, затем медленно опустите ноги, не касаясь пола. Повторите движение плавно и контролируемо.",
},
{
title: "Подходы",
description: "Выполните 3 подхода по 12 повторений с отдыхом 60 секунд между подходами.",
},
{
title: "Перерыв",
description: "Отдыхайте 60 секунд между подходами. Дышите спокойно и расслабьте мышцы.",
},
{
title: "Динамика и статика",
description:
"Динамическая фаза: подъем и опускание ног выполняется плавно, 2 секунды вверх, 2 секунды вниз. Статическая фаза: удержание ног в верхней точке на 2 секунды.",
},
]
return (
<div className="bg-gray-50 w-full h-full overflow-auto">
<div className="mt-36 mb-90 min-h-screen max-w-4xl mx-auto">
<HeaderNav item='Надо разобраться?' text='упражнение' />
{/* Video/Image Section */}
<div className="px-4 sm:px-6 mt-10 mb-6">
<div className="glass-morphism rounded-3xl overflow-hidden shadow-2xl border border-white/20 backdrop-blur-2xl">
<div className="relative">
<video
src={video}
className="w-full h-120 object-cover"
autoPlay
loop
muted
playsInline
/>
<div className="absolute inset-0 bg-gradient-to-t from-black/30 via-transparent to-black/10"></div>
<div className="absolute inset-0 flex items-center justify-center">
<button
onClick={() => setIsPlaying(!isPlaying)}
className={
isPlaying
? "w-20 h-20 bg-transparent backdrop-blur-xl rounded-full flex items-center justify-center shadow-2xl transition-all duration-300 transform hover:scale-110 border border-cyan-50 opacity-40"
: "rounded-full w-20 h-20 flex items-center justify-center backdrop-blur-xl opacity-70"
}
>
{isPlaying ? <PauseIcon /> : <PlayIcon />}
</button>
</div>
{/* Live indicators */}
{isPlaying && (
<div className="absolute top-4 left-4 flex items-center space-x-2">
<div className="w-3 h-3 bg-orange-500 rounded-full animate-pulse "></div>
<span className="text-white text-sm font-bold bg-black/30 px-3 py-1 rounded-full backdrop-blur-sm">
Выполнение
</span>
</div>
)}
{/* Timer Display */}
<div className="absolute top-4 right-4 bg-cyan-50 backdrop-blur-sm px-3 py-1 rounded-xl">
<span className="text-gray-800 text-sm font-bold">{formatTime(currentTime)}</span>
</div>
</div>
</div>
</div>
{/* Exercise Steps - Vertical Scroll */}
<div className="px-4 sm:px-6 space-y-4 mb-6">
{exerciseSteps.map((step, index) => (
<div
key={index}
className="bg-white rounded-2xl p-5 border border-gray-200 shadow-lg hover:shadow-xl transition-all duration-300"
>
<div className="flex items-start space-x-4">
<div>
<h3 className="text-lg font-black text-gray-800 mb-2">{step.title}</h3>
<p className="text-gray-600 leading-relaxed text-sm sm:text-base">{step.description}</p>
</div>
</div>
</div>
))}
</div>
{/* Fixed Timer at Bottom */}
<div className="fixed bottom-36 left-0 right-0 bg-white opacity-95 border-t border-white/20 px-4 sm:px-6 py-4 shadow-2xl z-30">
<div className="max-w-md mx-auto">
<div className="flex items-center justify-between mb-3">
<div className="flex items-center space-x-2">
<div className="w-2 h-2 bg-green-400 rounded-full animate-pulse"></div>
<span className="text-sm font-bold text-gray-700">
Подход {currentSet} из {totalSets}
</span>
</div>
<span className="text-sm font-black text-gray-700">
{formatTime(currentTime)} / {formatTime(totalTime)}
</span>
</div>
<div className="bg-white/30 rounded-full h-3 mb-4 overflow-hidden">
<div
className="bg-gradient-to-r from-[#2BACBE] via-cyan-500 to-cyan-700 h-3 rounded-full transition-all duration-1000 shadow-sm"
style={{ width: `${progress}%` }}
></div>
</div>
<div className="flex space-x-3">
<button
onClick={() => setIsPlaying(!isPlaying)}
className={`flex-1 font-bold py-3 px-4 rounded-xl transition-all duration-300 transform hover:scale-105 flex items-center justify-center space-x-2 ${isPlaying
? "bg-gray-400 text-white shadow-lg"
: "bg-[#2BACBE] hover:bg-[#2099A8] text-white shadow-lg"
}`}
>
{isPlaying ? (
<>
<PauseIcon /> <span>Пауза</span>
</>
) : (
<>
<PlayIcon /> <span className="backdrop-blur-xl">Начать</span>
</>
)}
</button>
<button
onClick={() => {
setCurrentTime(0)
setIsPlaying(false)
}}
className="px-6 py-3 bg-white text-gray-800 font-bold rounded-xl transition-all duration-300 hover:shadow-lg border border-gray-200 flex items-center justify-center"
>
<RefreshIcon />
</button>
<button
onClick={() => setCurrentSet((prev) => Math.min(prev + 1, totalSets))}
className="px-6 py-3 bg-white text-gray-800 font-bold rounded-xl transition-all duration-300 hover:shadow-lg border border-gray-200 flex items-center justify-center"
>
<CheckIcon />
</button>
</div>
</div>
</div>
<BottomNavigation />
</div>
</div>
)
}
export default Exercise