diff --git a/src/components/sections/FirmLifeGallerySection.tsx b/src/components/sections/FirmLifeGallerySection.tsx new file mode 100644 index 0000000..2f35d17 --- /dev/null +++ b/src/components/sections/FirmLifeGallerySection.tsx @@ -0,0 +1,251 @@ +'use client'; + +import { useState, useMemo, useEffect } from 'react'; +import Image from 'next/image'; +import { X, ChevronLeft, ChevronRight } from 'lucide-react'; +import Modal from '@/components/ui/Modal'; + +interface Photo { + id: number; + src: string; + alt: string; + caption: string; + date: string; + category: 'Offices' | 'Attorneys' | 'Client Events' | 'Community Outreach'; +} + +const photos: Photo[] = [ + { + id: 1, + src: 'https://images.pexels.com/photos/37726678/pexels-photo-37726678.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'law legal atmosphere interior', + caption: 'Gumede & Partners main office, Pietermaritzburg', + date: '10 Jun 2025', + category: 'Offices', + }, + { + id: 2, + src: 'https://images.pexels.com/photos/7875996/pexels-photo-7875996.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'law professional', + caption: 'Senior partner Martha Gumede in consultation', + date: '18 May 2025', + category: 'Attorneys', + }, + { + id: 3, + src: 'https://images.pexels.com/photos/5673483/pexels-photo-5673483.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'filterable photo grid firm life law', + caption: 'Annual client appreciation braai', + date: '5 Apr 2025', + category: 'Client Events', + }, + { + id: 4, + src: 'https://images.pexels.com/photos/2084277/pexels-photo-2084277.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'filterable photo grid firm life', + caption: 'Pro bono legal clinic at Imbali township', + date: '22 Mar 2025', + category: 'Community Outreach', + }, + { + id: 5, + src: 'https://images.pexels.com/photos/5673483/pexels-photo-5673483.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'filterable photo grid firm life law', + caption: 'Boardroom where key deals are closed', + date: '2 Mar 2025', + category: 'Offices', + }, + { + id: 6, + src: 'https://images.pexels.com/photos/2084277/pexels-photo-2084277.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'filterable photo grid firm life', + caption: 'Associate Thabo Dlamini preparing for court', + date: '28 Feb 2025', + category: 'Attorneys', + }, + { + id: 7, + src: 'https://images.pexels.com/photos/37726678/pexels-photo-37726678.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'law legal atmosphere interior', + caption: 'Real estate seminar with local investors', + date: '15 Jan 2025', + category: 'Client Events', + }, + { + id: 8, + src: 'https://images.pexels.com/photos/7875996/pexels-photo-7875996.jpeg?auto=compress&cs=tinysrgb&h=650&w=940', + alt: 'law professional', + caption: 'Wills Week – free estate planning workshop', + date: '10 Dec 2024', + category: 'Community Outreach', + }, +]; + +const categories = ['All', 'Offices', 'Attorneys', 'Client Events', 'Community Outreach'] as const; + +export default function FirmLifeGallerySection() { + const [filter, setFilter] = useState('All'); + const [lightboxIndex, setLightboxIndex] = useState(null); + + const filteredPhotos = useMemo(() => { + if (filter === 'All') return photos; + return photos.filter((p) => p.category === filter); + }, [filter]); + + const closeLightbox = () => setLightboxIndex(null); + const goToPrev = () => { + setLightboxIndex((prev) => { + if (prev === null || filteredPhotos.length === 0) return prev; + return (prev - 1 + filteredPhotos.length) % filteredPhotos.length; + }); + }; + const goToNext = () => { + setLightboxIndex((prev) => { + if (prev === null || filteredPhotos.length === 0) return prev; + return (prev + 1) % filteredPhotos.length; + }); + }; + + useEffect(() => { + if (lightboxIndex === null) return; + const handleKey = (e: KeyboardEvent) => { + if (e.key === 'Escape') closeLightbox(); + if (e.key === 'ArrowLeft') goToPrev(); + if (e.key === 'ArrowRight') goToNext(); + }; + window.addEventListener('keydown', handleKey); + return () => window.removeEventListener('keydown', handleKey); + }, [lightboxIndex]); // eslint-disable-line react-hooks/exhaustive-deps + + const currentPhoto = lightboxIndex !== null ? filteredPhotos[lightboxIndex] : null; + + return ( + + ); +}