diff --git a/src/app/globals.css b/src/app/globals.css index c6a31d0..74fa896 100644 --- a/src/app/globals.css +++ b/src/app/globals.css @@ -48,3 +48,14 @@ body { :focus-visible { @apply outline-2 outline-offset-2 outline-[#c9a96e]; } + +/* ===== Scrollbar hide utility ===== */ + +.scrollbar-hide { + -ms-overflow-style: none; + scrollbar-width: none; +} + +.scrollbar-hide::-webkit-scrollbar { + display: none; +} diff --git a/src/components/sections/Schedule.tsx b/src/components/sections/Schedule.tsx index 265fe63..19e531d 100644 --- a/src/components/sections/Schedule.tsx +++ b/src/components/sections/Schedule.tsx @@ -5,6 +5,7 @@ import { MapPin, Clock, User, X, ChevronDown } from "lucide-react"; import { siteContent } from "@/data/content"; import { SectionHeading } from "@/components/ui/SectionHeading"; import { Reveal } from "@/components/ui/Reveal"; +import type { ScheduleDay } from "@/types/content"; const TYPE_DOT: Record = { "Exotic Pole Dance": "bg-[#c9a96e]", @@ -15,6 +16,63 @@ const TYPE_DOT: Record = { type StatusFilter = "all" | "hasSlots" | "recruiting"; +function DayCard({ day }: { day: ScheduleDay }) { + return ( +
+ {/* Day header */} +
+
+ + {day.dayShort} + + + {day.day} + +
+
+ + {/* Classes */} +
+ {day.classes.map((cls, i) => ( +
+
+
+ + {cls.time} +
+ {cls.hasSlots && ( + + есть места + + )} + {cls.recruiting && ( + + набор + + )} +
+
+ + {cls.trainer} +
+
+
+ + {cls.type} +
+ {cls.level && ( + + {cls.level} + + )} +
+
+ ))} +
+
+ ); +} + export function Schedule() { const { schedule } = siteContent; const [locationIndex, setLocationIndex] = useState(0); @@ -71,7 +129,7 @@ export function Schedule() { setFilterStatus("all"); } - const pillBase = "inline-flex items-center gap-1.5 rounded-full px-3 py-1 text-[11px] font-medium transition-all duration-200 cursor-pointer"; + const pillBase = "inline-flex items-center gap-1.5 rounded-full px-3 py-1 text-[11px] font-medium transition-all duration-200 cursor-pointer whitespace-nowrap"; const pillActive = "bg-[#c9a96e]/20 text-[#a08050] border border-[#c9a96e]/40 dark:text-[#d4b87a] dark:border-[#c9a96e]/30"; const pillInactive = "border border-neutral-200 text-neutral-500 hover:border-neutral-300 dark:border-white/[0.08] dark:text-white/35 dark:hover:border-white/15"; @@ -111,9 +169,9 @@ export function Schedule() { - {/* Compact filters */} + {/* Compact filters — scrollable on mobile */} -
+
{/* Class types */} {types.map((type) => ( ))} {/* Divider */} - + {/* Status filters */} {hasAnySlots && ( @@ -135,7 +193,7 @@ export function Schedule() { onClick={() => setFilterStatus(filterStatus === "hasSlots" ? "all" : "hasSlots")} className={`${pillBase} ${filterStatus === "hasSlots" ? "bg-emerald-500/20 text-emerald-700 border border-emerald-500/40 dark:text-emerald-400 dark:border-emerald-500/30" : pillInactive}`} > - + Есть места )} @@ -144,13 +202,13 @@ export function Schedule() { onClick={() => setFilterStatus(filterStatus === "recruiting" ? "all" : "recruiting")} className={`${pillBase} ${filterStatus === "recruiting" ? "bg-sky-500/20 text-sky-700 border border-sky-500/40 dark:text-sky-400 dark:border-sky-500/30" : pillInactive}`} > - + Набор )} {/* Divider */} - + {/* Trainer dropdown toggle */} @@ -193,68 +251,89 @@ export function Schedule() {
- {/* Day columns — full width */} + {/* Mobile: compact agenda list */} + +
+ {filteredDays.length > 0 ? ( +
+ {filteredDays.map((day) => ( +
+ {/* Day header */} +
+ + {day.dayShort} + + + {day.day} + +
+ + {/* Class rows */} +
+ {day.classes.map((cls, i) => ( +
+ {/* Time */} + + {cls.time} + + + {/* Info */} +
+
+ + {cls.trainer} + + {cls.hasSlots && ( + + места + + )} + {cls.recruiting && ( + + набор + + )} + {cls.level && ( + + {cls.level} + + )} +
+
+ + {cls.type} +
+
+
+ ))} +
+
+ ))} +
+ ) : ( +
+ Нет занятий по выбранным фильтрам +
+ )} +
+
+ + {/* Desktop: grid layout */}
= 7 ? "xl:grid-cols-7" : filteredDays.length >= 4 ? "xl:grid-cols-" + filteredDays.length : "xl:grid-cols-4"}`} - style={filteredDays.length < 4 && filteredDays.length > 0 ? { maxWidth: filteredDays.length * 320 + (filteredDays.length - 1) * 12, marginInline: "auto" } : undefined} + className={`mt-8 hidden sm:grid grid-cols-1 gap-3 px-4 sm:px-6 lg:px-8 xl:px-6 ${filteredDays.length >= 7 ? "sm:grid-cols-2 lg:grid-cols-4 xl:grid-cols-7" : filteredDays.length >= 4 ? "sm:grid-cols-2 lg:grid-cols-3 xl:grid-cols-" + filteredDays.length : filteredDays.length === 3 ? "sm:grid-cols-2 lg:grid-cols-3" : filteredDays.length === 2 ? "sm:grid-cols-2" : "justify-items-center"}`} + style={filteredDays.length === 1 ? undefined : filteredDays.length <= 3 && filteredDays.length > 0 ? { maxWidth: filteredDays.length * 340 + (filteredDays.length - 1) * 12, marginInline: "auto" } : undefined} > {filteredDays.map((day) => (
- {/* Day header */} -
-
- - {day.dayShort} - - - {day.day} - -
-
- - {/* Classes */} -
- {day.classes.map((cls, i) => ( -
-
-
- - {cls.time} -
- {cls.hasSlots && ( - - есть места - - )} - {cls.recruiting && ( - - набор - - )} -
-
- - {cls.trainer} -
-
-
- - {cls.type} -
- {cls.level && ( - - {cls.level} - - )} -
-
- ))} -
+
))}