diff --git a/client/public/videos/board-intro-archive.mp4 b/client/public/videos/board-intro-archive.mp4
new file mode 100644
index 0000000..476306f
Binary files /dev/null and b/client/public/videos/board-intro-archive.mp4 differ
diff --git a/client/public/videos/community-01.mp4 b/client/public/videos/community-01.mp4
new file mode 100644
index 0000000..29cc136
Binary files /dev/null and b/client/public/videos/community-01.mp4 differ
diff --git a/client/public/videos/community-02.mp4 b/client/public/videos/community-02.mp4
new file mode 100644
index 0000000..1c3e26a
Binary files /dev/null and b/client/public/videos/community-02.mp4 differ
diff --git a/client/public/videos/community-03.mp4 b/client/public/videos/community-03.mp4
new file mode 100644
index 0000000..78e5b40
Binary files /dev/null and b/client/public/videos/community-03.mp4 differ
diff --git a/client/public/videos/community-04.mp4 b/client/public/videos/community-04.mp4
new file mode 100644
index 0000000..ad1e18f
Binary files /dev/null and b/client/public/videos/community-04.mp4 differ
diff --git a/client/public/videos/community-05.mp4 b/client/public/videos/community-05.mp4
new file mode 100644
index 0000000..025443a
Binary files /dev/null and b/client/public/videos/community-05.mp4 differ
diff --git a/client/src/App.tsx b/client/src/App.tsx
index e61c175..bac1178 100644
--- a/client/src/App.tsx
+++ b/client/src/App.tsx
@@ -10,6 +10,7 @@ import Bylaws from './components/Bylaws';
import Sponsors from './components/Sponsors';
import MeetBoard from './components/Meet-Board';
import Gallery from './components/Gallery';
+import VideoGallery from './components/VideoGallery';
/* import ComingSoon from './components/ComingSoon'; */
import JoinMCDi from './components/JoinMCDi';
@@ -28,6 +29,7 @@ const App: React.FC = () => {
} />
} />
} />
+ } />
} />
diff --git a/client/src/components/Header.tsx b/client/src/components/Header.tsx
index 3d59ef9..87670ba 100644
--- a/client/src/components/Header.tsx
+++ b/client/src/components/Header.tsx
@@ -74,7 +74,8 @@ const Header: React.FC = () => {
setIsMenuOpen(false)}>Home
setIsMenuOpen(false)}>About MCDi
setIsMenuOpen(false)}>Calendar
- setIsMenuOpen(false)}>Gallery
+ setIsMenuOpen(false)}>Photo Gallery
+ setIsMenuOpen(false)}>Video Gallery
setIsMenuOpen(false)}>Join MCDi
@@ -157,7 +158,8 @@ const AboutDropdown: React.FC = () => {
Meet MCDi Board
Bylaws
Minutes
- Gallery
+ Photo Gallery
+ Video Gallery
Sponsors
diff --git a/client/src/components/VideoGallery.tsx b/client/src/components/VideoGallery.tsx
new file mode 100644
index 0000000..defa5cc
--- /dev/null
+++ b/client/src/components/VideoGallery.tsx
@@ -0,0 +1,270 @@
+import React, { useState, useRef, useEffect } from 'react';
+import { motion, AnimatePresence } from 'framer-motion';
+import { FaPlay, FaPause, FaStop } from 'react-icons/fa';
+
+interface VideoItem {
+ id: number;
+ videoUrl: string;
+ title: string;
+ thumbnail?: string;
+}
+
+const videoData: VideoItem[] = [
+ {
+ id: 1,
+ videoUrl: '/videos/community-01.mp4',
+ title: 'Community Event Video 1',
+ },
+ {
+ id: 2,
+ videoUrl: '/videos/community-02.mp4',
+ title: 'Community Event Video 2',
+ },
+ {
+ id: 3,
+ videoUrl: '/videos/community-03.mp4',
+ title: 'Community Event Video 3',
+ },
+ {
+ id: 4,
+ videoUrl: '/videos/community-04.mp4',
+ title: 'Community Event Video 4',
+ },
+ {
+ id: 5,
+ videoUrl: '/videos/community-05.mp4',
+ title: 'Community Event Video 5',
+ },
+ {
+ id: 6,
+ videoUrl: '/videos/board-intro-archive.mp4',
+ title: 'Board Introduction Archive',
+ },
+];
+
+const VideoGallery: React.FC = () => {
+ const [selectedVideo, setSelectedVideo] = useState(null);
+ const videoRef = useRef(null);
+ const [isPlaying, setIsPlaying] = useState(false);
+ const [showControls, setShowControls] = useState(true);
+ const [progress, setProgress] = useState(0);
+ const controlsTimeoutRef = useRef(null);
+
+ const openVideo = (item: VideoItem) => {
+ setSelectedVideo(item);
+ setIsPlaying(false);
+ setProgress(0);
+ };
+
+ const closeVideo = () => {
+ if (videoRef.current) {
+ videoRef.current.pause();
+ videoRef.current.currentTime = 0;
+ }
+ setSelectedVideo(null);
+ setIsPlaying(false);
+ };
+
+ const togglePlay = () => {
+ if (videoRef.current) {
+ if (isPlaying) {
+ videoRef.current.pause();
+ } else {
+ videoRef.current.play();
+ }
+ setIsPlaying(!isPlaying);
+ }
+ };
+
+ const handleStop = () => {
+ if (videoRef.current) {
+ videoRef.current.pause();
+ videoRef.current.currentTime = 0;
+ setIsPlaying(false);
+ }
+ };
+
+ const handleTimeUpdate = () => {
+ if (videoRef.current) {
+ const progress = (videoRef.current.currentTime / videoRef.current.duration) * 100;
+ setProgress(progress);
+ }
+ };
+
+ const handleSeek = (e: React.ChangeEvent) => {
+ if (videoRef.current) {
+ const seekTime = (parseFloat(e.target.value) / 100) * videoRef.current.duration;
+ videoRef.current.currentTime = seekTime;
+ }
+ };
+
+ const handleMouseMove = () => {
+ setShowControls(true);
+ if (controlsTimeoutRef.current) {
+ clearTimeout(controlsTimeoutRef.current);
+ }
+ controlsTimeoutRef.current = setTimeout(() => {
+ if (isPlaying) {
+ setShowControls(false);
+ }
+ }, 3000);
+ };
+
+ useEffect(() => {
+ return () => {
+ if (controlsTimeoutRef.current) {
+ clearTimeout(controlsTimeoutRef.current);
+ }
+ };
+ }, []);
+
+ return (
+
+
+ Video Gallery
+
+ {/* Video Grid */}
+
+ {videoData.map((item) => (
+
openVideo(item)}
+ >
+
+
+ ))}
+
+
+
+ {/* Video Modal */}
+
+ {selectedVideo && (
+
+ e.stopPropagation()}
+ onMouseMove={handleMouseMove}
+ onMouseLeave={() => isPlaying && setShowControls(false)}
+ >
+ {/* Close Button */}
+
+
+ {/* Video Container */}
+
+
+
+ {/* Video Controls */}
+
+ {showControls && (
+
+
+
+ {selectedVideo.title}
+
+
+
+
+
+
+
+
+ )}
+
+
+
+
+ )}
+
+
+ );
+};
+
+export default VideoGallery;