From 55531d863f0c6a482282db2b3d3e2e7c5a1e8d85 Mon Sep 17 00:00:00 2001 From: Ankit Gupta <76108902+ankitXD@users.noreply.github.com> Date: Sun, 6 Jul 2025 20:51:35 +0530 Subject: [PATCH 01/16] feat: Add Student Notes, Profile, Results, and Test Dashboard pages with functionality for managing study materials, user profiles, examination results, and online tests --- client/src/components/Header.jsx | 6 - client/src/hooks/use-mobile.jsx | 19 ++ client/src/hooks/use-toast.js | 167 ++++++++++ client/src/pages/About.jsx | 258 +++++++++++++++ client/src/pages/Admin.jsx | 388 ++++++++++++++++++++++ client/src/pages/Announcements.jsx | 249 ++++++++++++++ client/src/pages/Certificate.jsx | 256 +++++++++++++++ client/src/pages/Contact.jsx | 263 +++++++++++++++ client/src/pages/Courses.jsx | 270 +++++++++++++++ client/src/pages/Dashboard.jsx | 255 +++++++++++++++ client/src/pages/Gallery.jsx | 202 ++++++++++++ client/src/pages/HomePage.jsx | 0 client/src/pages/Login.jsx | 178 ++++++++++ client/src/pages/Notes.jsx | 212 ++++++++++++ client/src/pages/Profile.jsx | 347 ++++++++++++++++++++ client/src/pages/Register.jsx | 268 +++++++++++++++ client/src/pages/Resources.jsx | 291 +++++++++++++++++ client/src/pages/Results.jsx | 453 ++++++++++++++++++++++++++ client/src/pages/ResultsDashboard.jsx | 226 +++++++++++++ client/src/pages/Scholarship.jsx | 366 +++++++++++++++++++++ client/src/pages/TestDashboard.jsx | 285 ++++++++++++++++ client/src/pages/Tests.jsx | 309 ++++++++++++++++++ 22 files changed, 5262 insertions(+), 6 deletions(-) create mode 100644 client/src/hooks/use-mobile.jsx create mode 100644 client/src/hooks/use-toast.js create mode 100644 client/src/pages/Certificate.jsx delete mode 100644 client/src/pages/HomePage.jsx create mode 100644 client/src/pages/Notes.jsx create mode 100644 client/src/pages/Profile.jsx create mode 100644 client/src/pages/ResultsDashboard.jsx create mode 100644 client/src/pages/TestDashboard.jsx diff --git a/client/src/components/Header.jsx b/client/src/components/Header.jsx index 7c65d7a..9c426dd 100644 --- a/client/src/components/Header.jsx +++ b/client/src/components/Header.jsx @@ -23,12 +23,6 @@ export default function Header() { > Home - - Courses - { + const mql = window.matchMedia(`(max-width: ${MOBILE_BREAKPOINT - 1}px)`) + const onChange = () => { + setIsMobile(window.innerWidth < MOBILE_BREAKPOINT) + } + mql.addEventListener("change", onChange) + setIsMobile(window.innerWidth < MOBILE_BREAKPOINT) + return () => mql.removeEventListener("change", onChange) + }, []) + + return !!isMobile +} \ No newline at end of file diff --git a/client/src/hooks/use-toast.js b/client/src/hooks/use-toast.js new file mode 100644 index 0000000..fa12065 --- /dev/null +++ b/client/src/hooks/use-toast.js @@ -0,0 +1,167 @@ +"use client"; + +// Inspired by react-hot-toast library +import * as React from "react"; + +const TOAST_LIMIT = 1; +const TOAST_REMOVE_DELAY = 1000000; + +/** + * @typedef {Object} ToasterToast + * @property {string} id + * @property {React.ReactNode} [title] + * @property {React.ReactNode} [description] + * @property {any} [action] + * @property {boolean} [open] + * @property {function} [onOpenChange] + */ + + +let count = 0; + +function genId() { + count = (count + 1) % Number.MAX_SAFE_INTEGER; + return count.toString(); +} + +/** + * @typedef {Object} State + * @property {ToasterToast[]} toasts + */ + +const toastTimeouts = new Map(); + +const addToRemoveQueue = (toastId) => { + if (toastTimeouts.has(toastId)) { + return; + } + + const timeout = setTimeout(() => { + toastTimeouts.delete(toastId); + dispatch({ + type: "REMOVE_TOAST", + toastId: toastId, + }); + }, TOAST_REMOVE_DELAY); + + toastTimeouts.set(toastId, timeout); +}; + +export const reducer = (state, action) => { + switch (action.type) { + case "ADD_TOAST": + return { + ...state, + toasts: [action.toast, ...state.toasts].slice(0, TOAST_LIMIT), + }; + + case "UPDATE_TOAST": + return { + ...state, + toasts: state.toasts.map((t) => + t.id === action.toast.id ? { ...t, ...action.toast } : t + ), + }; + + case "DISMISS_TOAST": { + const { toastId } = action; + + // ! Side effects ! - This could be extracted into a dismissToast() action, + // but I'll keep it here for simplicity + if (toastId) { + addToRemoveQueue(toastId); + } else { + state.toasts.forEach((toast) => { + addToRemoveQueue(toast.id); + }); + } + + return { + ...state, + toasts: state.toasts.map((t) => + t.id === toastId || toastId === undefined + ? { + ...t, + open: false, + } + : t + ), + }; + } + case "REMOVE_TOAST": + if (action.toastId === undefined) { + return { + ...state, + toasts: [], + }; + } + return { + ...state, + toasts: state.toasts.filter((t) => t.id !== action.toastId), + }; + default: + return state; + } +}; + +const listeners = []; + +let memoryState = { toasts: [] }; + +function dispatch(action) { + memoryState = reducer(memoryState, action); + listeners.forEach((listener) => { + listener(memoryState); + }); +} + +function toast(props) { + const id = genId(); + + const update = (props) => + dispatch({ + type: "UPDATE_TOAST", + toast: { ...props, id }, + }); + const dismiss = () => dispatch({ type: "DISMISS_TOAST", toastId: id }); + + dispatch({ + type: "ADD_TOAST", + toast: { + ...props, + id, + open: true, + onOpenChange: (open) => { + if (!open) dismiss(); + }, + }, + }); + + return { + id: id, + dismiss, + update, + }; +} + +function useToast() { + const [state, setState] = React.useState(memoryState); + + React.useEffect(() => { + listeners.push(setState); + return () => { + const index = listeners.indexOf(setState); + if (index > -1) { + listeners.splice(index, 1); + } + }; + }, [state]); + + return { + ...state, + toast, + dismiss: (toastId) => dispatch({ type: "DISMISS_TOAST", toastId }), + }; +} + +export { useToast, toast }; diff --git a/client/src/pages/About.jsx b/client/src/pages/About.jsx index e69de29..5c59534 100644 --- a/client/src/pages/About.jsx +++ b/client/src/pages/About.jsx @@ -0,0 +1,258 @@ +import { Header } from "../components/header" +import { Footer } from "../components/footer" +import { Card, CardContent } from "../components/ui/card" +import { Badge } from "../components/ui/badge" +import { Users, Award, BookOpen, Target, Heart, Star } from "lucide-react" + +const stats = [ + { icon: Users, label: "Students Trained", value: "5000+" }, + { icon: Award, label: "Success Rate", value: "95%" }, + { icon: BookOpen, label: "Courses Offered", value: "15+" }, + { icon: Target, label: "Years Experience", value: "10+" }, +] + +const team = [ + { + name: "Dr. Rajesh Kumar", + position: "Director & Founder", + qualification: "Ph.D in Computer Science", + experience: "15+ years", + image: "/placeholder.svg?height=200&width=200", + }, + { + name: "Prof. Sunita Sharma", + position: "Academic Head", + qualification: "M.Tech, B.Ed", + experience: "12+ years", + image: "/placeholder.svg?height=200&width=200", + }, + { + name: "Mr. Amit Gupta", + position: "Technical Lead", + qualification: "MCA, CCNA", + experience: "10+ years", + image: "/placeholder.svg?height=200&width=200", + }, +] + +const values = [ + { + icon: Heart, + title: "Student-Centric Approach", + description: "We prioritize individual student needs and provide personalized attention to ensure success.", + }, + { + icon: Star, + title: "Quality Education", + description: "Our curriculum is designed to meet industry standards and provide practical knowledge.", + }, + { + icon: Target, + title: "Result-Oriented", + description: "We focus on achieving measurable outcomes and helping students reach their goals.", + }, +] + +export default function AboutPage() { + return ( +
+
+
+ {/* Hero Section */} +
+
+
+

About EduInstitute

+

+ Empowering students with quality education and modern teaching methodologies for over a decade +

+
+
+
+ + {/* Stats Section */} +
+
+
+ {stats.map((stat, index) => ( + + + +

{stat.value}

+

{stat.label}

+
+
+ ))} +
+
+
+ + {/* Mission & Vision */} +
+
+
+ + +

Our Mission

+

+ To provide accessible, high-quality education that empowers students to achieve their academic and + professional goals. We strive to create an inclusive learning environment that fosters creativity, + critical thinking, and lifelong learning. +

+
+
+ + +

Our Vision

+

+ To be the leading educational institution that transforms lives through innovative teaching methods, + technology integration, and personalized learning experiences. We envision a future where every + student has the opportunity to excel and contribute meaningfully to society. +

+
+
+
+
+
+ + {/* Values */} +
+
+
+

Our Core Values

+

+ The principles that guide our approach to education and student development +

+
+
+ {values.map((value, index) => ( + + + +

{value.title}

+

{value.description}

+
+
+ ))} +
+
+
+ + {/* Team Section */} +
+
+
+

Meet Our Team

+

+ Experienced educators and industry professionals dedicated to your success +

+
+
+ {team.map((member, index) => ( + + +
+ {member.name} +
+

{member.name}

+ + {member.position} + +

{member.qualification}

+

{member.experience}

+
+
+ ))} +
+
+
+ + {/* Why Choose Us */} +
+
+
+

Why Choose EduInstitute?

+
+
+
+
+
+ 1 +
+
+

Expert Faculty

+

+ Learn from experienced professionals with deep industry knowledge and teaching expertise. +

+
+
+
+
+ 2 +
+
+

Modern Infrastructure

+

+ State-of-the-art facilities with latest technology and comfortable learning environment. +

+
+
+
+
+ 3 +
+
+

Personalized Attention

+

+ Small batch sizes ensure individual attention and customized learning approaches. +

+
+
+
+
+
+
+ 4 +
+
+

Comprehensive Study Material

+

+ Well-researched notes, assignments, and practice materials for thorough preparation. +

+
+
+
+
+ 5 +
+
+

Regular Assessment

+

+ Continuous evaluation through tests and assignments to track progress effectively. +

+
+
+
+
+ 6 +
+
+

Career Guidance

+

+ Professional counseling and career guidance to help students make informed decisions. +

+
+
+
+
+
+
+
+
+ ) +} diff --git a/client/src/pages/Admin.jsx b/client/src/pages/Admin.jsx index e69de29..cd71c60 100644 --- a/client/src/pages/Admin.jsx +++ b/client/src/pages/Admin.jsx @@ -0,0 +1,388 @@ +"use client" + +import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "../components/ui/card" +import { Button } from "../components/ui/button" +import { Badge } from "../components/ui/badge" +import { Tabs, TabsContent, TabsList, TabsTrigger } from "../components/ui/tabs" +import { + Users, + BookOpen, + FileText, + Award, + Calendar, + Upload, + Settings, + BarChart3, + Plus, + Eye, + Download, +} from "lucide-react" +import Link from "next/link" + +// Mock data +const adminStats = { + totalStudents: 1250, + activeCourses: 5, + totalTests: 45, + pendingResults: 12, + todayAttendance: 89, + monthlyRevenue: 125000, +} + +const recentStudents = [ + { id: "STU001", name: "John Doe", course: "RS-CIT", status: "Active", joinDate: "2024-01-01" }, + { id: "STU002", name: "Jane Smith", course: "NIOS", status: "Active", joinDate: "2024-01-02" }, + { id: "STU003", name: "Mike Johnson", course: "CBSE", status: "Inactive", joinDate: "2024-01-03" }, +] + +const recentTests = [ + { id: 1, title: "RS-CIT Chapter 5", course: "RS-CIT", attempts: 45, avgScore: 78 }, + { id: 2, title: "NIOS Math Test", course: "NIOS", attempts: 32, avgScore: 82 }, + { id: 3, title: "CBSE Physics", course: "CBSE", attempts: 28, avgScore: 75 }, +] + +const attendanceData = [ + { date: "2024-01-05", present: 89, total: 100, percentage: 89 }, + { date: "2024-01-04", present: 92, total: 100, percentage: 92 }, + { date: "2024-01-03", present: 87, total: 100, percentage: 87 }, +] + +export default function AdminDashboard() { + return ( +
+ {/* Header */} +
+
+
+

Admin Dashboard

+

Manage your institute efficiently

+
+
+ + +
+
+
+ +
+ {/* Stats Overview */} +
+ + +
+
+

Total Students

+

{adminStats.totalStudents}

+
+ +
+
+
+ + + +
+
+

Active Courses

+

{adminStats.activeCourses}

+
+ +
+
+
+ + + +
+
+

Total Tests

+

{adminStats.totalTests}

+
+ +
+
+
+ + + +
+
+

Pending Results

+

{adminStats.pendingResults}

+
+ +
+
+
+ + + +
+
+

Today's Attendance

+

{adminStats.todayAttendance}%

+
+ +
+
+
+ + + +
+
+

Monthly Revenue

+

₹{adminStats.monthlyRevenue.toLocaleString()}

+
+ +
+
+
+
+ + {/* Main Content Tabs */} + + + Overview + Students + Courses + Tests + Attendance + + + +
+ {/* Recent Students */} + + + Recent Students + Latest student registrations + + +
+ {recentStudents.map((student) => ( +
+
+

{student.name}

+

+ {student.id} • {student.course} +

+
+ {student.status} +
+ ))} +
+ +
+
+ + {/* Recent Tests */} + + + Test Performance + Recent test statistics + + +
+ {recentTests.map((test) => ( +
+
+

{test.title}

+

+ {test.course} • {test.attempts} attempts +

+
+
+

{test.avgScore}%

+

Avg Score

+
+
+ ))} +
+ +
+
+
+
+ + + + +
+
+ Student Management + Manage student information and enrollment +
+ +
+
+ +
+ + + + +
+
+
+
+ + + + +
+
+ Course Management + Manage courses and study materials +
+ +
+
+ +
+ + + + +
+
+
+
+ + + + +
+
+ Test Management + Create and manage online tests +
+ +
+
+ +
+ + + + +
+
+
+
+ + + + +
+
+ Attendance Management + Track and manage student attendance +
+ +
+
+ +
+
+ + + +
+ +
+

Recent Attendance

+ {attendanceData.map((day, index) => ( +
+
+

{new Date(day.date).toLocaleDateString()}

+

+ {day.present}/{day.total} students present +

+
+ = 90 ? "default" : day.percentage >= 75 ? "secondary" : "destructive" + } + > + {day.percentage}% + +
+ ))} +
+
+
+
+
+
+
+
+ ) +} diff --git a/client/src/pages/Announcements.jsx b/client/src/pages/Announcements.jsx index e69de29..4ac4bcb 100644 --- a/client/src/pages/Announcements.jsx +++ b/client/src/pages/Announcements.jsx @@ -0,0 +1,249 @@ +import { Header } from "../components/header" +import { Footer } from "../components/footer" +import { Card, CardContent, CardHeader, CardTitle } from "../components/ui/card" +import { Badge } from "../components/ui/badge" +import { Button } from "../components/ui/button" +import { Input } from "../components/ui/input" +import { Calendar, Bell, Search, Filter, Pin, Clock } from "lucide-react" + +const announcements = [ + { + id: 1, + title: "New Batch Starting for RS-CIT Course", + content: + "We are excited to announce that a new batch for RS-CIT course will be starting from February 1st, 2024. Limited seats available. Early bird discount of 20% for registrations before January 20th.", + type: "Course", + isUrgent: true, + isPinned: true, + publishDate: "2024-01-05", + expiryDate: "2024-01-31", + targetAudience: "All", + }, + { + id: 2, + title: "NIOS Exam Schedule Released", + content: + "The National Institute of Open Schooling has released the examination schedule for April 2024 session. Students can download their admit cards from the official portal starting January 15th.", + type: "Exam", + isUrgent: false, + isPinned: true, + publishDate: "2024-01-03", + expiryDate: "2024-04-30", + targetAudience: "NIOS Students", + }, + { + id: 3, + title: "Scholarship Applications Open", + content: + "Merit-based scholarship applications are now open for eligible students. Applications must be submitted with required documents before the deadline. Contact our counseling team for assistance.", + type: "Scholarship", + isUrgent: true, + isPinned: false, + publishDate: "2024-01-01", + expiryDate: "2024-02-15", + targetAudience: "All", + }, + { + id: 4, + title: "Winter Break Schedule", + content: + "The institute will remain closed from December 25th to January 2nd for winter break. Regular classes will resume from January 3rd. Online support will be available during the break.", + type: "General", + isUrgent: false, + isPinned: false, + publishDate: "2023-12-20", + expiryDate: "2024-01-03", + targetAudience: "All", + }, + { + id: 5, + title: "New Computer Lab Inauguration", + content: + "We are pleased to announce the inauguration of our new state-of-the-art computer laboratory with 50 latest computers. The lab will be operational from January 10th.", + type: "Infrastructure", + isUrgent: false, + isPinned: false, + publishDate: "2023-12-15", + expiryDate: "2024-01-31", + targetAudience: "All", + }, + { + id: 6, + title: "Parent-Teacher Meeting", + content: + "Monthly parent-teacher meeting is scheduled for January 20th from 10 AM to 4 PM. Parents can discuss their ward's progress with respective faculty members.", + type: "Meeting", + isUrgent: false, + isPinned: false, + publishDate: "2023-12-10", + expiryDate: "2024-01-20", + targetAudience: "Parents", + }, +] + +const categories = ["All", "Course", "Exam", "Scholarship", "General", "Infrastructure", "Meeting"] + +export default function AnnouncementsPage() { + const pinnedAnnouncements = announcements.filter((a) => a.isPinned) + const regularAnnouncements = announcements.filter((a) => !a.isPinned) + + return ( +
+
+
+ {/* Hero Section */} +
+
+
+

Announcements

+

+ Stay updated with the latest news, events, and important information +

+
+
+
+ + {/* Search and Filter */} +
+
+
+
+ + +
+ +
+
+ + Category: + +
+
+
+
+
+ + {/* Pinned Announcements */} + {pinnedAnnouncements.length > 0 && ( +
+
+
+ +

Pinned Announcements

+
+
+ {pinnedAnnouncements.map((announcement) => ( + + +
+
+ {announcement.type} + {announcement.isUrgent && ( + + + Urgent + + )} + +
+
+ + {new Date(announcement.publishDate).toLocaleDateString()} +
+
+ {announcement.title} +
+ +

{announcement.content}

+
+ {announcement.targetAudience} + {announcement.expiryDate && ( +
+ + Expires: {new Date(announcement.expiryDate).toLocaleDateString()} +
+ )} +
+
+
+ ))} +
+
+
+ )} + + {/* Regular Announcements */} +
+
+

Recent Announcements

+
+ {regularAnnouncements.map((announcement) => ( + + +
+
+ {announcement.type} + {announcement.isUrgent && ( + + + Urgent + + )} +
+
+ + {new Date(announcement.publishDate).toLocaleDateString()} +
+
+ {announcement.title} +
+ +

{announcement.content}

+
+ {announcement.targetAudience} + {announcement.expiryDate && ( +
+ + Expires: {new Date(announcement.expiryDate).toLocaleDateString()} +
+ )} +
+
+
+ ))} +
+
+
+ + {/* Notification Signup */} +
+
+ + + +

Never Miss an Update

+

+ Subscribe to get instant notifications about important announcements and updates +

+
+ + +
+

+ You can unsubscribe at any time. We respect your privacy. +

+
+
+
+
+
+
+ ) +} diff --git a/client/src/pages/Certificate.jsx b/client/src/pages/Certificate.jsx new file mode 100644 index 0000000..a4b7122 --- /dev/null +++ b/client/src/pages/Certificate.jsx @@ -0,0 +1,256 @@ +"use client" + +import { Card, CardContent, CardDescription, CardHeader, CardTitle } from "../components/ui/card" +import { Button } from "../components/ui/button" +import { Badge } from "../components/ui/badge" +import { Download, Eye, Calendar, Award, Share, Printer } from "lucide-react" +import { Link } from "react-router-dom"; + +const certificates = [ + { + id: 1, + title: "RS-CIT Course Completion Certificate", + course: "RS-CIT", + issueDate: "2024-01-20", + certificateNumber: "RSCIT/2024/001", + status: "Issued", + grade: "A", + percentage: 85, + validUntil: "Lifetime", + downloadUrl: "/certificates/rscit-001.pdf", + verificationUrl: "https://verify.eduinstitute.com/RSCIT2024001", + }, + { + id: 2, + title: "Computer Basics Proficiency Certificate", + course: "RS-CIT", + issueDate: "2024-01-15", + certificateNumber: "CB/2024/001", + status: "Issued", + grade: "B+", + percentage: 78, + validUntil: "Lifetime", + downloadUrl: "/certificates/cb-001.pdf", + verificationUrl: "https://verify.eduinstitute.com/CB2024001", + }, +] + +const achievements = [ + { + id: 1, + title: "Perfect Attendance", + description: "100% attendance for the entire course duration", + icon: "🏆", + earnedDate: "2024-01-20", + }, + { + id: 2, + title: "Quick Learner", + description: "Completed course 2 weeks ahead of schedule", + icon: "⚡", + earnedDate: "2024-01-18", + }, + { + id: 3, + title: "Top Performer", + description: "Scored in top 10% of the batch", + icon: "🌟", + earnedDate: "2024-01-15", + }, +] + +export default function StudentCertificatesPage() { + return ( +
+ {/* Header */} +
+
+
+

Certificates & Achievements

+

Your earned certificates and achievements

+
+ +
+
+ +
+ {/* Stats Overview */} +
+ + +
+
+

Total Certificates

+

{certificates.length}

+
+ +
+
+
+ + +
+
+

Achievements

+

{achievements.length}

+
+ +
+
+
+ + +
+
+

Average Grade

+

A-

+
+ +
+
+
+
+ + {/* Certificates Section */} +
+

My Certificates

+ + {certificates.map((certificate) => ( + + +
+
+ {certificate.title} + +
+ + Issued: {new Date(certificate.issueDate).toLocaleDateString()} +
+ {certificate.course} +
+
+ + {certificate.status} + +
+
+ + + {/* Certificate Details */} +
+
+

Certificate Details

+
+
+ Certificate Number: + {certificate.certificateNumber} +
+
+ Grade Achieved: + {certificate.grade} +
+
+ Percentage: + {certificate.percentage}% +
+
+ Valid Until: + {certificate.validUntil} +
+
+
+ +
+

Verification

+
+

Verification URL:

+

+ {certificate.verificationUrl} +

+
+
+
+ + {/* Actions */} +
+ + + + +
+
+
+ ))} +
+ + {/* Achievements Section */} +
+

Achievements & Badges

+ +
+ {achievements.map((achievement) => ( + + +
{achievement.icon}
+

{achievement.title}

+

{achievement.description}

+
+ + Earned: {new Date(achievement.earnedDate).toLocaleDateString()} +
+
+
+ ))} +
+
+ + {/* Certificate Verification Info */} + + + Certificate Verification + How to verify your certificates + + +
+
+
+

For Employers

+

+ Employers can verify the authenticity of certificates using the verification URL provided with each + certificate. +

+
+
+

Digital Security

+

+ All certificates are digitally signed and secured with blockchain technology for tamper-proof + verification. +

+
+
+
+ +
+
+
+
+
+
+ ) +} diff --git a/client/src/pages/Contact.jsx b/client/src/pages/Contact.jsx index e69de29..fb751a0 100644 --- a/client/src/pages/Contact.jsx +++ b/client/src/pages/Contact.jsx @@ -0,0 +1,263 @@ +"use client"; + +import React from "react"; +import { useState } from "react"; +import { Header } from "../components/header"; +import { Footer } from "../components/footer"; +import { Button } from "../components/ui/button"; +import { Input } from "../components/ui/input"; +import { Label } from "../components/ui/label"; +import { Textarea } from "../components/ui/textarea"; +import { + Card, + CardContent, + CardDescription, + CardHeader, + CardTitle, +} from "../components/ui/card"; +import { MapPin, Phone, Mail, Clock, Send } from "lucide-react"; +import { useToast } from "../hooks/use-toast"; + +export default function ContactPage() { + const [isSubmitting, setIsSubmitting] = useState(false); + const { toast } = useToast(); + + const handleSubmit = async (e) => { + e.preventDefault(); + setIsSubmitting(true); + + // Simulate form submission + setTimeout(() => { + setIsSubmitting(false); + toast({ + title: "Message Sent!", + description: "Thank you for contacting us. We'll get back to you soon.", + }); + }, 2000); + }; + + return ( +
+
+
+ {/* Hero Section */} +
+
+
+

+ Contact Us +

+

+ Get in touch with us for admissions, course information, or any + queries +

+
+
+
+ + {/* Contact Information & Form */} +
+
+
+ {/* Contact Information */} +
+
+

Get in Touch

+

+ We're here to help you with your educational journey. Reach + out to us through any of the following channels. +

+
+ +
+ + +
+ +
+

Address

+

+ 123 Education Street +
+ Learning City, State 123456 +
+ India +

+
+
+
+
+ + + +
+ +
+

Phone

+

+ +91 98765 43210 +
+ +91 98765 43211 (Admissions) +

+
+
+
+
+ + + +
+ +
+

Email

+

+ info@eduinstitute.com +
+ admissions@eduinstitute.com +

+
+
+
+
+ + + +
+ +
+

Office Hours

+

+ Monday - Friday: 9:00 AM - 6:00 PM +
+ Saturday: 9:00 AM - 4:00 PM +
+ Sunday: Closed +

+
+
+
+
+
+
+ + {/* Contact Form */} + + + Send us a Message + + Fill out the form below and we'll get back to you as soon as + possible. + + + +
+
+
+ + +
+
+ + +
+
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ +