From 70694da2e2a47ec49d71050f3ca764b5826a4ad9 Mon Sep 17 00:00:00 2001 From: Amudieshwar A G Date: Fri, 7 Aug 2026 11:20:01 +0530 Subject: [PATCH 01/11] feat(notes): integrate official RIT Moodle portal hub for notes and PYQs --- src/pages/Notes/Notes.tsx | 272 ++++++++++++++------------------------ 1 file changed, 99 insertions(+), 173 deletions(-) diff --git a/src/pages/Notes/Notes.tsx b/src/pages/Notes/Notes.tsx index 9e4c34e..7e48e37 100644 --- a/src/pages/Notes/Notes.tsx +++ b/src/pages/Notes/Notes.tsx @@ -1,8 +1,10 @@ import { useState, useRef, useEffect } from 'react'; import { useSearchParams } from 'react-router-dom'; import { motion } from 'framer-motion'; -import { Search, Download, Filter, BookOpen, FileText, ScrollText, BookMarked, ChevronRight, ArrowLeft, ExternalLink, Code, Globe, GitBranch, Cloud, Palette, Shield, DollarSign, BarChart3, Users, Megaphone, TrendingUp, UserCheck, ClipboardList, ShoppingCart, Cpu, Activity, LayoutGrid, Layers, Zap, Settings, Gauge, Radio, Wifi, Bot, Sun, Wrench, Binary, BatteryCharging, CircuitBoard, ShieldCheck, BrainCircuit, FlaskConical, Lock, Terminal, Dna, Microscope, Sparkles, Smartphone, Monitor, Server, CheckCircle2, Database, Briefcase, AlertTriangle } from 'lucide-react'; +import { Search, Download, Filter, BookOpen, FileText, ScrollText, BookMarked, ChevronRight, ArrowLeft, ExternalLink, Code, Globe, GitBranch, Cloud, Palette, Shield, DollarSign, BarChart3, Users, Megaphone, TrendingUp, UserCheck, ClipboardList, ShoppingCart, Cpu, Activity, LayoutGrid, Layers, Zap, Settings, Gauge, Radio, Wifi, Bot, Sun, Wrench, Binary, BatteryCharging, CircuitBoard, ShieldCheck, BrainCircuit, FlaskConical, Lock, Terminal, Dna, Microscope, Sparkles, Smartphone, Monitor, Server, CheckCircle2, Database, Briefcase, AlertTriangle, RefreshCw } from 'lucide-react'; import SectionTitle from '@/components/SectionTitle/SectionTitle'; + +const MOODLE_URL = 'http://182.74.17.142/moodle/login/index.php'; import { getBackendUrl } from '@/lib/utils'; import { StaggerContainer, StaggerItem } from '@/components/AnimatedContainer/AnimatedContainer'; import { TOOLKIT_ITEMS, DEPARTMENTS } from '@/constants'; @@ -1432,27 +1434,7 @@ export default function Notes() { )}
- {/* Under Development Banner */} - -
-
- -
-
-
Under Development
-
- Currently displaying sample mock notes & syllabus data. Official semester notes repository integration is in progress. -
-
-
- - Mock Data Active - -
+ {selectedToolkit ? ( (() => { @@ -1936,169 +1918,113 @@ export default function Notes() { })() ) : (
- {/* Search + Filters */} +
+ {/* Moodle Academic Portal Hero Hub */} - {/* Search */} -
- - setSearchQuery(e.target.value)} - className="w-full pl-11 pr-4 py-3 rounded-xl border border-[#E5E7EB] text-sm text-[#1E293B] placeholder-[#94A3B8] focus:outline-none focus:border-[#F97316] transition-colors" - style={{ fontFamily: 'Inter, sans-serif' }} - /> -
+ {/* Subtle Decorative Background Glow */} +
+
-
- {/* Type Filter */} -
- - {['all', 'notes', 'pyq', 'syllabus'].map((type) => ( - - ))} +
+ {/* Header Badge */} +
+ + Official RIT Learning Management System
- {/* Semester Filter */} -
- {SEMESTERS.slice(0, 3).map((sem) => ( - - ))} + {/* Main Heading */} +

+ Access Academic Notes & Study Materials on{' '} + + Moodle + +

+ +

+ All official semester notes, previous year question papers (PYQs), syllabus data, and lab manuals are hosted directly on the official Rajalakshmi Institute of Technology Moodle server. +

+ + {/* Primary Launch Action Buttons */} +
+ + + Launch Official RIT Moodle Portal + + +
- {/* Subject Dropdown */} - {selectedSem !== 'All' && ( -
- Subject: - + {/* Feature Highlights Grid */} +
+
+
+ +
+
+ 100% Direct & Secure +
+
+ Authenticates directly on official college server 182.74.17.142. +
- )} + +
+
+ +
+
+ Official Semester Notes +
+
+ Complete 1st to 8th Semester course notes, PYQs, and assignments. +
+
+ +
+
+ +
+
+ Student Login +
+
+ Log in using your RIT Register Number and official Moodle password. +
+
+
+ + {/* Technical Security Note */} +
+ ℹ️ Security Note: To protect student session privacy and prevent clickjacking attacks, RIT's Moodle server enforces opening the portal directly in a secure browser tab rather than inside third-party frames (X-Frame-Options: SAMEORIGIN). +
- - {/* Results */} - - {filtered.map((note) => { - const typeConfig = TYPE_COLORS[note.type] || { bg: '#F1F5F9', text: '#475569', icon: BookOpen }; - const TypeIcon = typeConfig.icon; - return ( - - -
- {/* Visual PDF Preview Icon */} -
-
- PDF -
-
-
-
-
-
-
- - {/* Text Details */} -
-
-
-
- -
- - {note.type} - -
-

- {note.title} -

-

- {note.subject} • Sem {note.semester} -

-
-
-
- - {/* Metadata Line */} -
-
- {note.downloads} downloads · {note.fileSize} - PDF -
- {note.uploadedAt ? `Updated ${note.uploadedAt}` : 'Recently'} -
- - {/* Download Button */} - handleDownload(note.id, note.downloadUrl)} - className="w-full flex items-center justify-center gap-2 py-2.5 rounded-xl text-sm font-semibold text-white cursor-pointer" - style={{ - fontFamily: 'Poppins, sans-serif', - background: 'linear-gradient(135deg, #F97316, #FB923C)', - }} - > - - Download - - - - ); - })} - +
{/* Toolkit Section */}
From e1f3fe2ec25bdf46438f2b36488b419debe93026 Mon Sep 17 00:00:00 2001 From: Amudieshwar A G Date: Fri, 7 Aug 2026 11:20:01 +0530 Subject: [PATCH 02/11] feat(notes): integrate official RIT Moodle portal hub for notes and PYQs --- src/pages/Notes/Notes.tsx | 272 ++++++++++++++------------------------ 1 file changed, 99 insertions(+), 173 deletions(-) diff --git a/src/pages/Notes/Notes.tsx b/src/pages/Notes/Notes.tsx index 9e4c34e..7e48e37 100644 --- a/src/pages/Notes/Notes.tsx +++ b/src/pages/Notes/Notes.tsx @@ -1,8 +1,10 @@ import { useState, useRef, useEffect } from 'react'; import { useSearchParams } from 'react-router-dom'; import { motion } from 'framer-motion'; -import { Search, Download, Filter, BookOpen, FileText, ScrollText, BookMarked, ChevronRight, ArrowLeft, ExternalLink, Code, Globe, GitBranch, Cloud, Palette, Shield, DollarSign, BarChart3, Users, Megaphone, TrendingUp, UserCheck, ClipboardList, ShoppingCart, Cpu, Activity, LayoutGrid, Layers, Zap, Settings, Gauge, Radio, Wifi, Bot, Sun, Wrench, Binary, BatteryCharging, CircuitBoard, ShieldCheck, BrainCircuit, FlaskConical, Lock, Terminal, Dna, Microscope, Sparkles, Smartphone, Monitor, Server, CheckCircle2, Database, Briefcase, AlertTriangle } from 'lucide-react'; +import { Search, Download, Filter, BookOpen, FileText, ScrollText, BookMarked, ChevronRight, ArrowLeft, ExternalLink, Code, Globe, GitBranch, Cloud, Palette, Shield, DollarSign, BarChart3, Users, Megaphone, TrendingUp, UserCheck, ClipboardList, ShoppingCart, Cpu, Activity, LayoutGrid, Layers, Zap, Settings, Gauge, Radio, Wifi, Bot, Sun, Wrench, Binary, BatteryCharging, CircuitBoard, ShieldCheck, BrainCircuit, FlaskConical, Lock, Terminal, Dna, Microscope, Sparkles, Smartphone, Monitor, Server, CheckCircle2, Database, Briefcase, AlertTriangle, RefreshCw } from 'lucide-react'; import SectionTitle from '@/components/SectionTitle/SectionTitle'; + +const MOODLE_URL = 'http://182.74.17.142/moodle/login/index.php'; import { getBackendUrl } from '@/lib/utils'; import { StaggerContainer, StaggerItem } from '@/components/AnimatedContainer/AnimatedContainer'; import { TOOLKIT_ITEMS, DEPARTMENTS } from '@/constants'; @@ -1432,27 +1434,7 @@ export default function Notes() { )}
- {/* Under Development Banner */} - -
-
- -
-
-
Under Development
-
- Currently displaying sample mock notes & syllabus data. Official semester notes repository integration is in progress. -
-
-
- - Mock Data Active - -
+ {selectedToolkit ? ( (() => { @@ -1936,169 +1918,113 @@ export default function Notes() { })() ) : (
- {/* Search + Filters */} +
+ {/* Moodle Academic Portal Hero Hub */} - {/* Search */} -
- - setSearchQuery(e.target.value)} - className="w-full pl-11 pr-4 py-3 rounded-xl border border-[#E5E7EB] text-sm text-[#1E293B] placeholder-[#94A3B8] focus:outline-none focus:border-[#F97316] transition-colors" - style={{ fontFamily: 'Inter, sans-serif' }} - /> -
+ {/* Subtle Decorative Background Glow */} +
+
-
- {/* Type Filter */} -
- - {['all', 'notes', 'pyq', 'syllabus'].map((type) => ( - - ))} +
+ {/* Header Badge */} +
+ + Official RIT Learning Management System
- {/* Semester Filter */} -
- {SEMESTERS.slice(0, 3).map((sem) => ( - - ))} + {/* Main Heading */} +

+ Access Academic Notes & Study Materials on{' '} + + Moodle + +

+ +

+ All official semester notes, previous year question papers (PYQs), syllabus data, and lab manuals are hosted directly on the official Rajalakshmi Institute of Technology Moodle server. +

+ + {/* Primary Launch Action Buttons */} +
+ + + Launch Official RIT Moodle Portal + + +
- {/* Subject Dropdown */} - {selectedSem !== 'All' && ( -
- Subject: - + {/* Feature Highlights Grid */} +
+
+
+ +
+
+ 100% Direct & Secure +
+
+ Authenticates directly on official college server 182.74.17.142. +
- )} + +
+
+ +
+
+ Official Semester Notes +
+
+ Complete 1st to 8th Semester course notes, PYQs, and assignments. +
+
+ +
+
+ +
+
+ Student Login +
+
+ Log in using your RIT Register Number and official Moodle password. +
+
+
+ + {/* Technical Security Note */} +
+ ℹ️ Security Note: To protect student session privacy and prevent clickjacking attacks, RIT's Moodle server enforces opening the portal directly in a secure browser tab rather than inside third-party frames (X-Frame-Options: SAMEORIGIN). +
- - {/* Results */} - - {filtered.map((note) => { - const typeConfig = TYPE_COLORS[note.type] || { bg: '#F1F5F9', text: '#475569', icon: BookOpen }; - const TypeIcon = typeConfig.icon; - return ( - - -
- {/* Visual PDF Preview Icon */} -
-
- PDF -
-
-
-
-
-
-
- - {/* Text Details */} -
-
-
-
- -
- - {note.type} - -
-

- {note.title} -

-

- {note.subject} • Sem {note.semester} -

-
-
-
- - {/* Metadata Line */} -
-
- {note.downloads} downloads · {note.fileSize} - PDF -
- {note.uploadedAt ? `Updated ${note.uploadedAt}` : 'Recently'} -
- - {/* Download Button */} - handleDownload(note.id, note.downloadUrl)} - className="w-full flex items-center justify-center gap-2 py-2.5 rounded-xl text-sm font-semibold text-white cursor-pointer" - style={{ - fontFamily: 'Poppins, sans-serif', - background: 'linear-gradient(135deg, #F97316, #FB923C)', - }} - > - - Download - - - - ); - })} - +
{/* Toolkit Section */}
From 5c8754a155ac1d24efa493ac49d7ed54b34f4c33 Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 11:24:07 +0530 Subject: [PATCH 03/11] ci: update git notification scripts with email credentials --- scripts/post-receive.sh | 7 +++---- scripts/send_git_email.py | 6 +++--- 2 files changed, 6 insertions(+), 7 deletions(-) diff --git a/scripts/post-receive.sh b/scripts/post-receive.sh index adb36df..22d7aab 100644 --- a/scripts/post-receive.sh +++ b/scripts/post-receive.sh @@ -1,9 +1,8 @@ #!/bin/bash -# Configuration (or set in environment variables on VPS) -export SENDER_EMAIL="your-gmail-id@gmail.com" -export SENDER_PASSWORD="your-16-digit-app-password" -export RECIPIENT_EMAIL="your-recipient-email@gmail.com" +export SENDER_EMAIL="krishnaowoxd@gmail.com" +export SENDER_PASSWORD="qkwy lwtc snlr pree" +export RECIPIENT_EMAIL="krishnaowoxd@gmail.com" while read oldrev newrev refname do diff --git a/scripts/send_git_email.py b/scripts/send_git_email.py index 4a57bd4..b719b58 100644 --- a/scripts/send_git_email.py +++ b/scripts/send_git_email.py @@ -7,9 +7,9 @@ from email.mime.multipart import MIMEMultipart # Load configuration from environment or fallback defaults SMTP_SERVER = os.environ.get("SMTP_SERVER", "smtp.gmail.com") SMTP_PORT = int(os.environ.get("SMTP_PORT", 587)) -SENDER_EMAIL = os.environ.get("SENDER_EMAIL", "YOUR_EMAIL@gmail.com") -SENDER_PASSWORD = os.environ.get("SENDER_PASSWORD", "YOUR_GMAIL_APP_PASSWORD") -RECIPIENT_EMAIL = os.environ.get("RECIPIENT_EMAIL", "YOUR_EMAIL@gmail.com") +SENDER_EMAIL = os.environ.get("SENDER_EMAIL", "krishnaowoxd@gmail.com") +SENDER_PASSWORD = os.environ.get("SENDER_PASSWORD", "qkwy lwtc snlr pree") +RECIPIENT_EMAIL = os.environ.get("RECIPIENT_EMAIL", "krishnaowoxd@gmail.com") if len(sys.argv) < 7: print("Usage: python send_git_email.py ") From e1d7dee45f48b433d4635e2b73e116377879d9ba Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 11:25:50 +0530 Subject: [PATCH 04/11] test(ci): verify automated email push report notification system --- scripts/post-receive.sh | 2 ++ 1 file changed, 2 insertions(+) diff --git a/scripts/post-receive.sh b/scripts/post-receive.sh index 22d7aab..f8c392f 100644 --- a/scripts/post-receive.sh +++ b/scripts/post-receive.sh @@ -1,4 +1,6 @@ #!/bin/bash +# Test commit to verify automated email push report notification system + export SENDER_EMAIL="krishnaowoxd@gmail.com" export SENDER_PASSWORD="qkwy lwtc snlr pree" From 31a1b66b747adb59526743878b989df2088dff73 Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 11:27:44 +0530 Subject: [PATCH 05/11] ci: update recipient email to dorutoslayer@gmail.com --- scripts/post-receive.sh | 2 +- scripts/send_git_email.py | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/scripts/post-receive.sh b/scripts/post-receive.sh index f8c392f..61145a1 100644 --- a/scripts/post-receive.sh +++ b/scripts/post-receive.sh @@ -4,7 +4,7 @@ export SENDER_EMAIL="krishnaowoxd@gmail.com" export SENDER_PASSWORD="qkwy lwtc snlr pree" -export RECIPIENT_EMAIL="krishnaowoxd@gmail.com" +export RECIPIENT_EMAIL="dorutoslayer@gmail.com" while read oldrev newrev refname do diff --git a/scripts/send_git_email.py b/scripts/send_git_email.py index b719b58..af36aaa 100644 --- a/scripts/send_git_email.py +++ b/scripts/send_git_email.py @@ -9,7 +9,7 @@ SMTP_SERVER = os.environ.get("SMTP_SERVER", "smtp.gmail.com") SMTP_PORT = int(os.environ.get("SMTP_PORT", 587)) SENDER_EMAIL = os.environ.get("SENDER_EMAIL", "krishnaowoxd@gmail.com") SENDER_PASSWORD = os.environ.get("SENDER_PASSWORD", "qkwy lwtc snlr pree") -RECIPIENT_EMAIL = os.environ.get("RECIPIENT_EMAIL", "krishnaowoxd@gmail.com") +RECIPIENT_EMAIL = os.environ.get("RECIPIENT_EMAIL", "dorutoslayer@gmail.com") if len(sys.argv) < 7: print("Usage: python send_git_email.py ") From 31e562ab89db9c1b1c20ba6bed681243e9865d9e Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 11:38:26 +0530 Subject: [PATCH 06/11] fix(bus-map): remove polyline route line overlay --- src/components/BusRouteMap/BusRouteMap.tsx | 16 ++-------------- 1 file changed, 2 insertions(+), 14 deletions(-) diff --git a/src/components/BusRouteMap/BusRouteMap.tsx b/src/components/BusRouteMap/BusRouteMap.tsx index c470ad9..5ff1340 100644 --- a/src/components/BusRouteMap/BusRouteMap.tsx +++ b/src/components/BusRouteMap/BusRouteMap.tsx @@ -1,5 +1,5 @@ import { useEffect, useMemo, useState } from 'react'; -import { MapContainer, TileLayer, Marker, Popup, Polyline, useMap } from 'react-leaflet'; +import { MapContainer, TileLayer, Marker, Popup, useMap } from 'react-leaflet'; import L from 'leaflet'; import 'leaflet/dist/leaflet.css'; import type { BusRoute } from '@/types'; @@ -178,19 +178,7 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png" /> - {/* Polyline Route Path */} - {pathCoordinates.length > 0 && selectedRoute && ( - - )} + {/* Live GPS Bus Markers */} {Object.entries(allLiveLocations).map(([rNum, loc]) => { From 0e22ad7b66a955e886d225932f2bc831f1a67714 Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 11:58:22 +0530 Subject: [PATCH 07/11] docs: add email automation setup guide --- EMAIL_AUTOMATION_GUIDE.md | 103 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 103 insertions(+) create mode 100644 EMAIL_AUTOMATION_GUIDE.md diff --git a/EMAIL_AUTOMATION_GUIDE.md b/EMAIL_AUTOMATION_GUIDE.md new file mode 100644 index 0000000..de641dc --- /dev/null +++ b/EMAIL_AUTOMATION_GUIDE.md @@ -0,0 +1,103 @@ +# 📧 Git Push & Deployment Email Notification Automation Guide + +This guide explains how the automated email reporting system for **Freshers-Hub** works, including configuration, scripts, and integration steps for VPS & Gitea CI/CD pipelines. + +--- + +## 🛠️ Overview of Included Scripts + +Two core scripts were added to the repository under the [`scripts/`](file:///f:/fresher/Freshers-Hub/scripts) directory: + +1. **[`scripts/send_git_email.py`](file:///f:/fresher/Freshers-Hub/scripts/send_git_email.py)**: Python script using `smtplib` to send rich HTML formatted deployment reports to `dorutoslayer@gmail.com` via Gmail SMTP. +2. **[`scripts/post-receive.sh`](file:///f:/fresher/Freshers-Hub/scripts/post-receive.sh)**: Shell script template for Git post-receive hook execution. + +--- + +## ⚙️ Configuration Details + +| Parameter | Value | +| :--- | :--- | +| **Sender Email** | `krishnaowoxd@gmail.com` | +| **App Password** | `qkwy lwtc snlr pree` | +| **Recipient Email** | `dorutoslayer@gmail.com` | +| **SMTP Host / Port** | `smtp.gmail.com:587` (TLS) | + +--- + +## 🚀 How to Enable Automated Email Reports + +### Method A: Add to VPS Webhook / Deployment Script (Recommended) + +If your VPS uses an automated webhook endpoint or deployment script (e.g. `/var/www/freshers-hub/deploy.sh`), add the python execution command right after `git pull`: + +```bash +#!/bin/bash +cd /var/www/freshers-hub + +# 1. Pull latest code +git pull origin main + +# 2. Build & Restart services (your existing deployment steps) +npm run build +systemctl restart springboot chatbot telegram-bot nginx + +# 3. 📧 Trigger Email Report Notification +/usr/bin/python3 /var/www/freshers-hub/scripts/send_git_email.py \ + "$(git rev-parse --abbrev-ref HEAD)" \ + "$(git log -1 --format='%an <%ae>')" \ + "$(git log -1 --format='%h')" \ + "$(git log -1 --format='%cd' --date=local)" \ + "$(git log -1 --format='%B')" \ + "$(git diff-tree --no-commit-id --name-status -r HEAD | head -n 15)" +``` + +--- + +### Method B: Configure Gitea Git Hook + +If using Gitea custom hooks: + +1. Go to your Gitea repository page: `https://git.rit-services.in/ShanmugaKrishnanSM/RIT-nexus`. +2. Navigate to **Settings** -> **Git Hooks**. +3. Edit **`post-receive`** (or `custom_hooks/post-receive`). +4. Paste the following hook script: + +```bash +#!/bin/bash +/usr/bin/python3 /var/www/freshers-hub/scripts/send_git_email.py \ + "main" \ + "$(git log -1 --format='%an <%ae>')" \ + "$(git log -1 --format='%h')" \ + "$(git log -1 --format='%cd' --date=local)" \ + "$(git log -1 --format='%B')" \ + "$(git diff-tree --no-commit-id --name-status -r HEAD | head -n 15)" +``` +5. Save changes. + +--- + +## 🧪 Manual Verification Command + +To verify that email delivery works from your VPS terminal: + +```bash +python3 /var/www/freshers-hub/scripts/send_git_email.py \ + "main" \ + "Test Author " \ + "cd30366" \ + "Fri Aug 7 11:55:00 2026" \ + "Testing email notification system" \ + "M src/components/BusRouteMap/BusRouteMap.tsx" +``` + +--- + +## 📊 Sample HTML Email Report Format + +When triggered, the recipient receives a formatted HTML email containing: +- **Branch**: `main` +- **Author**: Commit Author Name & Email +- **Commit Hash**: Short 7-character hash +- **Timestamp**: Date & Time of push +- **Commit Message**: Full commit message text +- **Changed Files**: List of top modified files (`M`, `A`, `D`) From 0a94f2fc6593cc12eba1e48253449b5dda0e3820 Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 12:00:33 +0530 Subject: [PATCH 08/11] fix(email): fix UnicodeEncodeError in print output, format App Password without spaces, add UTF-8 sys.stdout reconfigure --- EMAIL_AUTOMATION_GUIDE.md | 2 +- scripts/post-receive.sh | 2 +- scripts/send_git_email.py | 6 +++++- 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/EMAIL_AUTOMATION_GUIDE.md b/EMAIL_AUTOMATION_GUIDE.md index de641dc..267af47 100644 --- a/EMAIL_AUTOMATION_GUIDE.md +++ b/EMAIL_AUTOMATION_GUIDE.md @@ -18,7 +18,7 @@ Two core scripts were added to the repository under the [`scripts/`](file:///f:/ | Parameter | Value | | :--- | :--- | | **Sender Email** | `krishnaowoxd@gmail.com` | -| **App Password** | `qkwy lwtc snlr pree` | +| **App Password** | `qkwylwtcsnlrpree` (no spaces) | | **Recipient Email** | `dorutoslayer@gmail.com` | | **SMTP Host / Port** | `smtp.gmail.com:587` (TLS) | diff --git a/scripts/post-receive.sh b/scripts/post-receive.sh index 61145a1..8ede0a1 100644 --- a/scripts/post-receive.sh +++ b/scripts/post-receive.sh @@ -3,7 +3,7 @@ export SENDER_EMAIL="krishnaowoxd@gmail.com" -export SENDER_PASSWORD="qkwy lwtc snlr pree" +export SENDER_PASSWORD="qkwylwtcsnlrpree" export RECIPIENT_EMAIL="dorutoslayer@gmail.com" while read oldrev newrev refname diff --git a/scripts/send_git_email.py b/scripts/send_git_email.py index af36aaa..5479562 100644 --- a/scripts/send_git_email.py +++ b/scripts/send_git_email.py @@ -4,11 +4,15 @@ import os from email.mime.text import MIMEText from email.mime.multipart import MIMEMultipart +# Ensure UTF-8 output for terminal/logging +if hasattr(sys.stdout, 'reconfigure'): + sys.stdout.reconfigure(encoding='utf-8') + # Load configuration from environment or fallback defaults SMTP_SERVER = os.environ.get("SMTP_SERVER", "smtp.gmail.com") SMTP_PORT = int(os.environ.get("SMTP_PORT", 587)) SENDER_EMAIL = os.environ.get("SENDER_EMAIL", "krishnaowoxd@gmail.com") -SENDER_PASSWORD = os.environ.get("SENDER_PASSWORD", "qkwy lwtc snlr pree") +SENDER_PASSWORD = os.environ.get("SENDER_PASSWORD", "qkwylwtcsnlrpree").replace(" ", "") RECIPIENT_EMAIL = os.environ.get("RECIPIENT_EMAIL", "dorutoslayer@gmail.com") if len(sys.argv) < 7: From 5d02cfc7eeb3bd57c36e58bd77ad7e704e33cbe2 Mon Sep 17 00:00:00 2001 From: Shanmuga Krishnan S M Date: Fri, 7 Aug 2026 12:06:11 +0530 Subject: [PATCH 09/11] fix(bus-map): completely remove route polyline lines from map, focus strictly on clean map & live GPS bus markers --- src/components/BusRouteMap/BusRouteMap.tsx | 88 ++++++---------------- 1 file changed, 23 insertions(+), 65 deletions(-) diff --git a/src/components/BusRouteMap/BusRouteMap.tsx b/src/components/BusRouteMap/BusRouteMap.tsx index 5ff1340..107f4f2 100644 --- a/src/components/BusRouteMap/BusRouteMap.tsx +++ b/src/components/BusRouteMap/BusRouteMap.tsx @@ -17,35 +17,6 @@ L.Icon.Default.mergeOptions({ shadowUrl: markerShadow, }); -// Domain Boundary validation (Chennai and surrounding route regions) -const MIN_LAT = 12.65; -const MAX_LAT = 13.35; -const MIN_LNG = 79.25; -const MAX_LNG = 80.45; - -const isValidCoordinate = (lat?: number, lng?: number): boolean => { - if (lat === undefined || lng === undefined) return false; - return lat >= MIN_LAT && lat <= MAX_LAT && lng >= MIN_LNG && lng <= MAX_LNG; -}; - -const isRealStopCoordinate = (stop: { name: string; lat?: number; lng?: number }): boolean => { - if (stop.lat === undefined || stop.lng === undefined) return false; - if (!isValidCoordinate(stop.lat, stop.lng)) return false; - - const isRITCoord = Math.abs(stop.lat - 13.0118) < 0.001 && Math.abs(stop.lng - 80.0214) < 0.001; - const isRITName = - stop.name.toLowerCase().includes('rit') || - stop.name.toLowerCase().includes('campus') || - stop.name.toLowerCase().includes('college') || - stop.name.toLowerCase().includes('rajalakshmi'); - - if (isRITCoord && !isRITName) { - return false; - } - - return true; -}; - const liveBusIcon = L.divIcon({ html: `
🚌
`, className: '', @@ -60,14 +31,14 @@ const stoppedBusIcon = L.divIcon({ iconAnchor: [20, 20], }); -// Helper component to auto-pan and fit the map bounds to the active route -function MapUpdater({ bounds }: { bounds: L.LatLngBoundsExpression | null }) { +// Helper component to pan map to active bus marker when selected +function MapPanFocus({ center }: { center: [number, number] | null }) { const map = useMap(); useEffect(() => { - if (bounds && (bounds as any).length > 0) { - map.fitBounds(bounds, { padding: [60, 60], maxZoom: 14, animate: true }); + if (center) { + map.setView(center, 13, { animate: true }); } - }, [bounds, map]); + }, [center, map]); return null; } @@ -76,7 +47,7 @@ interface BusRouteMapProps { allRoutes: BusRoute[]; } -const DEFAULT_CENTER = [13.0118, 80.0214]; // RIT Campus default +const DEFAULT_CENTER: [number, number] = [13.0118, 80.0214]; // RIT Campus default export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { const [allLiveLocations, setAllLiveLocations] = useState< @@ -129,37 +100,26 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { return () => clearInterval(interval); }, []); - // Collect coordinates for polyline path - const pathCoordinates = useMemo(() => { - if (!selectedRoute) return []; + // Determine center focus point if a bus is live or selected + const activeFocusCenter = useMemo<[number, number] | null>(() => { + if (!selectedRoute) return null; - if (selectedRoute.polyline && selectedRoute.polyline.length > 0) { - return selectedRoute.polyline; + const normalizeRouteNum = (str: string) => (str || '').replace(/^[Rr]0*/, '').trim().toUpperCase(); + const matchLocKey = Object.keys(allLiveLocations).find( + (k) => normalizeRouteNum(k) === normalizeRouteNum(selectedRoute.number) + ); + + if (matchLocKey && allLiveLocations[matchLocKey]) { + const loc = allLiveLocations[matchLocKey]; + return [loc.latitude, loc.longitude]; } - const coords: [number, number][] = []; - - if (isValidCoordinate(selectedRoute.from_lat, selectedRoute.from_lng)) { - coords.push([selectedRoute.from_lat!, selectedRoute.from_lng!]); + if (selectedRoute.from_lat && selectedRoute.from_lng) { + return [selectedRoute.from_lat, selectedRoute.from_lng]; } - selectedRoute.stops.forEach((stop) => { - if (isRealStopCoordinate(stop)) { - coords.push([stop.lat!, stop.lng!]); - } - }); - - if (isValidCoordinate(selectedRoute.to_lat, selectedRoute.to_lng)) { - coords.push([selectedRoute.to_lat!, selectedRoute.to_lng!]); - } - - return coords; - }, [selectedRoute]); - - const mapBounds = useMemo(() => { - if (pathCoordinates.length === 0) return null; - return pathCoordinates as L.LatLngBoundsExpression; - }, [pathCoordinates]); + return DEFAULT_CENTER; + }, [selectedRoute, allLiveLocations]); return (
@@ -178,9 +138,7 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png" /> - - - {/* Live GPS Bus Markers */} + {/* Live GPS Bus Markers ONLY - No polyline routes */} {Object.entries(allLiveLocations).map(([rNum, loc]) => { const normalizeRouteNum = (str: string) => (str || '').replace(/^[Rr]0*/, '').trim().toUpperCase(); if (selectedRoute && normalizeRouteNum(selectedRoute.number) !== normalizeRouteNum(rNum)) return null; @@ -216,7 +174,7 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { ); })} - + {/* Floating Info Card on Selected Route */} From 17c981eec0af2bd613d63b0dc56da72c4b3b2b82 Mon Sep 17 00:00:00 2001 From: Devesh S Date: Fri, 7 Aug 2026 14:44:23 +0530 Subject: [PATCH 10/11] adjust ui and bus route --- .../src/main/resources/application.properties | 2 +- package-lock.json | 42 --- public/bus_routes.json | 344 +++++++++--------- src/components/BusRouteMap/BusRouteMap.tsx | 177 +++++++-- src/components/Navbar/Navbar.tsx | 36 +- src/constants/index.ts | 20 +- src/pages/Campus/Campus.tsx | 19 +- 7 files changed, 364 insertions(+), 276 deletions(-) diff --git a/backend/src/main/resources/application.properties b/backend/src/main/resources/application.properties index 2b88b38..34a60e6 100644 --- a/backend/src/main/resources/application.properties +++ b/backend/src/main/resources/application.properties @@ -1,7 +1,7 @@ # ─── DATABASE CONNECTION CONFIGURATION ─── spring.datasource.url=jdbc:postgresql://localhost:5432/rit_freshers_hub?sslmode=disable spring.datasource.username=postgres -spring.datasource.password=${DB_PASSWORD:Amudiesh22@.} +spring.datasource.password=${DB_PASSWORD:Devesh@54} # ─── JPA / HIBERNATE SETTINGS ─── spring.jpa.database-platform=org.hibernate.dialect.PostgreSQLDialect diff --git a/package-lock.json b/package-lock.json index 77ba273..202707c 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1776,9 +1776,6 @@ "x64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3602,9 +3599,6 @@ "arm" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3619,9 +3613,6 @@ "arm" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ @@ -3636,9 +3627,6 @@ "arm64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3653,9 +3641,6 @@ "arm64" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ @@ -3670,9 +3655,6 @@ "loong64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3687,9 +3669,6 @@ "loong64" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ @@ -3704,9 +3683,6 @@ "ppc64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3721,9 +3697,6 @@ "ppc64" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ @@ -3738,9 +3711,6 @@ "riscv64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3755,9 +3725,6 @@ "riscv64" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ @@ -3772,9 +3739,6 @@ "s390x" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3789,9 +3753,6 @@ "x64" ], "dev": true, - "libc": [ - "glibc" - ], "license": "MIT", "optional": true, "os": [ @@ -3806,9 +3767,6 @@ "x64" ], "dev": true, - "libc": [ - "musl" - ], "license": "MIT", "optional": true, "os": [ diff --git a/public/bus_routes.json b/public/bus_routes.json index 75aa07a..a28aeaf 100644 --- a/public/bus_routes.json +++ b/public/bus_routes.json @@ -65,14 +65,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.08095, - "lng": 80.27076 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.184827, "from_lng": 80.31205, - "to_lat": 13.08095, - "to_lng": 80.27076, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.184827, @@ -1146,14 +1146,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.08095, - "lng": 80.27076 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.128881, "from_lng": 80.290792, - "to_lat": 13.08095, - "to_lng": 80.27076, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.184827, @@ -2193,14 +2193,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.08095, - "lng": 80.27076 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.08095, "from_lng": 80.27076, - "to_lat": 13.08095, - "to_lng": 80.27076, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.184827, @@ -3258,14 +3258,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0761258, "from_lng": 80.270781, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.100598, @@ -4211,14 +4211,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.090276, "from_lng": 80.265585, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.118326, @@ -5196,14 +5196,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0884944, "from_lng": 80.1909707, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.118326, @@ -6207,14 +6207,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.089154, "from_lng": 80.230054, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.118326, @@ -7220,14 +7220,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.085333, "from_lng": 80.187393, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.085333, @@ -7847,14 +7847,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0293843, "from_lng": 80.2342825, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R05A", @@ -7934,14 +7934,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0617032, "from_lng": 80.2346118, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R06", @@ -8023,14 +8023,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.062841, "from_lng": 80.197105, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.066018, @@ -13337,14 +13337,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R10", @@ -15473,14 +15473,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.2820098, "from_lng": 80.2537109, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R13", @@ -15560,14 +15560,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R13A", @@ -15623,14 +15623,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.1001091, "from_lng": 80.2145485, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R14", @@ -15698,14 +15698,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R14B", @@ -15743,14 +15743,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.1305159, "from_lng": 79.9243758, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R15", @@ -15818,14 +15818,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R15A", @@ -15929,14 +15929,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R15B", @@ -16010,14 +16010,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R16", @@ -16085,14 +16085,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R16B", @@ -16184,14 +16184,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R17", @@ -16245,14 +16245,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.040666, "from_lng": 80.17222, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.054006, @@ -16860,14 +16860,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.040666, "from_lng": 80.17222, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.054006, @@ -17479,14 +17479,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 12.984051, "from_lng": 80.2175088, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R18A", @@ -17542,14 +17542,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R18B", @@ -17635,14 +17635,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 12.7871437, "from_lng": 80.219987, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R19", @@ -17704,14 +17704,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R19A", @@ -17749,14 +17749,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R20", @@ -17818,14 +17818,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R20A", @@ -17881,14 +17881,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R21", @@ -17944,14 +17944,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R22", @@ -18043,14 +18043,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R22A", @@ -18136,14 +18136,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R23", @@ -18211,14 +18211,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R24", @@ -18346,14 +18346,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R25", @@ -18409,14 +18409,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.1331405, "from_lng": 80.1701786, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R25A", @@ -18460,14 +18460,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R26", @@ -18535,14 +18535,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.1938755, "from_lng": 80.2685646, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R27", @@ -20662,14 +20662,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.1158603, "from_lng": 80.2300407, - "to_lat": 13.0118, - "to_lng": 80.0214, + "to_lat": 13.03868, + "to_lng": 80.045138, "polyline": [ [ 13.115889, @@ -21543,14 +21543,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R29A", @@ -21600,14 +21600,14 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 }, { "number": "R29B", @@ -21669,13 +21669,13 @@ { "name": "RIT Campus", "time": "07:40 AM", - "lat": 13.0118, - "lng": 80.0214 + "lat": 13.03868, + "lng": 80.045138 } ], "from_lat": 13.0118, "from_lng": 80.0214, - "to_lat": 13.0118, - "to_lng": 80.0214 + "to_lat": 13.03868, + "to_lng": 80.045138 } ] \ No newline at end of file diff --git a/src/components/BusRouteMap/BusRouteMap.tsx b/src/components/BusRouteMap/BusRouteMap.tsx index 107f4f2..ceb07d6 100644 --- a/src/components/BusRouteMap/BusRouteMap.tsx +++ b/src/components/BusRouteMap/BusRouteMap.tsx @@ -17,28 +17,74 @@ L.Icon.Default.mergeOptions({ shadowUrl: markerShadow, }); +// Glowing Live Bus Icon const liveBusIcon = L.divIcon({ - html: `
🚌
`, + html: `
🚌
`, className: '', iconSize: [40, 40], iconAnchor: [20, 20], }); +// Stopped Bus Icon const stoppedBusIcon = L.divIcon({ - html: `
🚌
`, + html: `
🚌
`, className: '', iconSize: [40, 40], iconAnchor: [20, 20], }); -// Helper component to pan map to active bus marker when selected -function MapPanFocus({ center }: { center: [number, number] | null }) { +// Helper: Create Clean Start Point Icon (Starting Location Name Only) +function createStartIcon(locationName: string) { + return L.divIcon({ + html: ` +
+ +
+ 📍 + ${locationName} +
+
+ `, + className: '', + iconSize: [160, 40], + iconAnchor: [80, 20], + }); +} + +// Helper: Create Clean Destination Point Icon (RIT Campus Only) +function createDestinationIcon(locationName: string) { + const displayName = locationName.includes('RIT') ? locationName : 'RIT Campus'; + return L.divIcon({ + html: ` +
+ +
+ 🏫 + ${displayName} +
+
+ `, + className: '', + iconSize: [160, 40], + iconAnchor: [80, 20], + }); +} + +// Helper component to auto-fit map view bounds when route changes +function MapPanFocus({ bounds }: { bounds: L.LatLngBoundsExpression | null }) { const map = useMap(); + useEffect(() => { - if (center) { - map.setView(center, 13, { animate: true }); + if (bounds) { + map.fitBounds(bounds, { + padding: [80, 80], + maxZoom: 14, + animate: true, + duration: 0.8, + }); } - }, [center, map]); + }, [bounds, map]); + return null; } @@ -47,7 +93,8 @@ interface BusRouteMapProps { allRoutes: BusRoute[]; } -const DEFAULT_CENTER: [number, number] = [13.0118, 80.0214]; // RIT Campus default +const RIT_CAMPUS_COORDS: [number, number] = [13.03868, 80.045138]; // True RIT Campus Kuthambakkam / Poonamallee +const DEFAULT_CENTER: [number, number] = RIT_CAMPUS_COORDS; export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { const [allLiveLocations, setAllLiveLocations] = useState< @@ -100,36 +147,52 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { return () => clearInterval(interval); }, []); - // Determine center focus point if a bus is live or selected - const activeFocusCenter = useMemo<[number, number] | null>(() => { + // Compute Start and Destination coordinates only + const routeData = useMemo(() => { if (!selectedRoute) return null; - const normalizeRouteNum = (str: string) => (str || '').replace(/^[Rr]0*/, '').trim().toUpperCase(); - const matchLocKey = Object.keys(allLiveLocations).find( - (k) => normalizeRouteNum(k) === normalizeRouteNum(selectedRoute.number) - ); - - if (matchLocKey && allLiveLocations[matchLocKey]) { - const loc = allLiveLocations[matchLocKey]; - return [loc.latitude, loc.longitude]; - } + // Start coordinates + let startCoords: [number, number] | null = null; + let startName = selectedRoute.from || 'Start Point'; if (selectedRoute.from_lat && selectedRoute.from_lng) { - return [selectedRoute.from_lat, selectedRoute.from_lng]; + startCoords = [selectedRoute.from_lat, selectedRoute.from_lng]; + } else if (selectedRoute.stops && selectedRoute.stops.length > 0) { + const firstStop = selectedRoute.stops[0]; + if (firstStop.lat && firstStop.lng) { + startCoords = [firstStop.lat, firstStop.lng]; + startName = firstStop.name || startName; + } } - return DEFAULT_CENTER; - }, [selectedRoute, allLiveLocations]); + // Destination is ALWAYS the true RIT Campus location (Kuthambakkam) + const destCoords: [number, number] = RIT_CAMPUS_COORDS; + const destName = 'RIT Campus'; + + // Compute bounding box for map view auto-fit (start & destination only) + const allPoints: [number, number][] = []; + if (startCoords) allPoints.push(startCoords); + if (destCoords) allPoints.push(destCoords); + + const bounds: L.LatLngBoundsExpression | null = + allPoints.length > 0 ? (allPoints as L.LatLngBoundsExpression) : null; + + return { + startCoords, + startName, + destCoords, + destName, + bounds, + }; + }, [selectedRoute]); return (
@@ -138,7 +201,52 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { url="https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png" /> - {/* Live GPS Bus Markers ONLY - No polyline routes */} + {/* ── SELECTED ROUTE MARKERS (Starting Point & RIT Campus Destination ONLY) ── */} + {selectedRoute && routeData && ( + <> + {/* START Point Marker */} + {routeData.startCoords && ( + + +
+ + 📍 ORIGIN / PICKUP + +

{routeData.startName}

+

+ Departure: {selectedRoute.departureTime || 'Early Morning'} +

+
+
+
+ )} + + {/* DESTINATION Point Marker (RIT Campus) */} + {routeData.destCoords && ( + + +
+ + 🏫 DESTINATION + +

{routeData.destName}

+

+ Arrival: {selectedRoute.arrivalTime || '08:30 AM'} +

+
+
+
+ )} + + )} + + {/* ── LIVE GPS BUS TRACKING MARKERS ── */} {Object.entries(allLiveLocations).map(([rNum, loc]) => { const normalizeRouteNum = (str: string) => (str || '').replace(/^[Rr]0*/, '').trim().toUpperCase(); if (selectedRoute && normalizeRouteNum(selectedRoute.number) !== normalizeRouteNum(rNum)) return null; @@ -174,7 +282,8 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) { ); })} - + {/* Auto fit map bounds when selected route changes */} +
{/* Floating Info Card on Selected Route */} @@ -183,21 +292,21 @@ export default function BusRouteMap({ selectedRoute }: BusRouteMapProps) {
{selectedRoute.number} {selectedRoute.name}
-

- 🏁 Start: {selectedRoute.from} ({selectedRoute.departureTime}) +

+ 📍 Start: {selectedRoute.from} ({selectedRoute.departureTime})

-

- 🏫 Destination: RIT Campus ({selectedRoute.arrivalTime}) +

+ 🏫 Destination: RIT Campus ({selectedRoute.arrivalTime})

-

- 📍 Stops: {selectedRoute.stops.length} mapped stops +

+ 📍 {selectedRoute.stops.length} mapped stops along route

diff --git a/src/components/Navbar/Navbar.tsx b/src/components/Navbar/Navbar.tsx index a27b419..a2f90bd 100644 --- a/src/components/Navbar/Navbar.tsx +++ b/src/components/Navbar/Navbar.tsx @@ -58,32 +58,32 @@ export default function Navbar() { initial={{ y: -100, opacity: 0 }} animate={{ y: 0, opacity: 1 }} transition={{ duration: 0.6, ease: 'easeOut' }} - className="fixed top-4 left-1/2 -translate-x-1/2 z-50 w-[95%] max-w-6xl transition-all duration-300 shadow-[0_8px_32px_rgba(0,0,0,0.25)]" + className="fixed top-4 left-1/2 -translate-x-1/2 z-50 w-[96%] max-w-7xl transition-all duration-300 shadow-[0_8px_32px_rgba(0,0,0,0.3)]" style={{ - background: 'linear-gradient(to right, rgba(15, 23, 42, 0.45) 0%, rgba(30, 41, 59, 0.35) 50%, rgba(15, 23, 42, 0.45) 100%)', + background: 'linear-gradient(to right, rgba(15, 23, 42, 0.75) 0%, rgba(30, 41, 59, 0.65) 50%, rgba(15, 23, 42, 0.75) 100%)', backdropFilter: 'blur(16px)', WebkitBackdropFilter: 'blur(16px)', borderRadius: '20px', - border: '1px solid rgba(255, 255, 255, 0.1)', + border: '1px solid rgba(255, 255, 255, 0.15)', }} > -
+
{/* Logo - RIT Event Hub Style */} - + {/* Logo Image */}
- + rit -
-
+
+
RAJALAKSHMI INSTITUTE OF TECHNOLOGY @@ -92,14 +92,14 @@ export default function Navbar() { {/* Desktop Nav */} -
+
{NAV_LINKS.map((link) => { const isActive = checkIsActive(link.path); return ( {/* Right Side: Auth + Mobile Toggle */} -
+
{/* Auth Section */} {isAuthenticated && user ? (
@@ -140,8 +140,8 @@ export default function Navbar() { {user.name.charAt(0).toUpperCase()}
)} -
- +
+ {user.name.split(' ')[0]} {isVerifiedStudent && ( @@ -150,7 +150,7 @@ export default function Navbar() { )}
- + {/* Profile Dropdown */} @@ -213,10 +213,10 @@ export default function Navbar() {
) : ( diff --git a/src/constants/index.ts b/src/constants/index.ts index cccb36c..34f9b46 100644 --- a/src/constants/index.ts +++ b/src/constants/index.ts @@ -4,7 +4,7 @@ import type { Feature, Stat, BusRoute, Faculty, Event, Club, Question, ToolkitIt export const NAV_LINKS = [ { label: 'Home', path: '/' }, { label: 'Notes', path: '/notes' }, - { label: 'Toolkit', path: '/notes?section=toolkit' }, + { label: 'Toolkit', path: '/toolkit' }, { label: 'Chatbot', path: '/ai-assistant' }, { label: 'Campus Map', path: '/campus' }, { label: 'Bus Routes', path: '/bus-routes' }, @@ -98,6 +98,24 @@ export const FEATURES: Feature[] = [ color: '#06B6D4', bgColor: '#ECFEFF', }, + { + id: 'collab', + icon: 'Code2', + title: 'Dev Collab', + description: 'Connect with peer developers, build campus projects, share repositories, and collaborate.', + path: '/collab', + color: '#6366F1', + bgColor: '#EEF2FF', + }, + { + id: 'leetcode', + icon: 'Trophy', + title: 'LeetCode Leaderboard', + description: 'Track peer coding rankings, solve daily problems, and compete on the campus leaderboard.', + path: '/leetcode', + color: '#F59E0B', + bgColor: '#FEF3C7', + }, ]; // ─── Bus Routes ────────────────────────────────────────────────────────────── diff --git a/src/pages/Campus/Campus.tsx b/src/pages/Campus/Campus.tsx index 4f7ff5d..92c052f 100644 --- a/src/pages/Campus/Campus.tsx +++ b/src/pages/Campus/Campus.tsx @@ -23,8 +23,9 @@ const BLUEPRINT_LEGEND = [ { id: 'a-block', label: 'A Block', color: '#60A5FA', bg: 'bg-blue-50/80', text: 'text-blue-900', border: 'border-blue-200' }, { id: 'b-block', label: 'B Block', color: '#93C5FD', bg: 'bg-blue-50/60', text: 'text-blue-900', border: 'border-blue-200' }, { id: 'c-block', label: 'C Block', color: '#BFDBFE', bg: 'bg-blue-50/40', text: 'text-blue-900', border: 'border-blue-200' }, + { id: 'h-block', label: 'H Block', color: '#C084FC', bg: 'bg-purple-50/80', text: 'text-purple-900', border: 'border-purple-200' }, { id: 'admin', label: 'Admin / Facility', color: '#FDBA74', bg: 'bg-orange-50/80', text: 'text-orange-950', border: 'border-orange-200' }, - { id: 'hostel', label: 'Hostel / Mess', color: '#C084FC', bg: 'bg-purple-50/80', text: 'text-purple-950', border: 'border-purple-200' }, + { id: 'hostel', label: 'Hostel / Mess', color: '#F472B6', bg: 'bg-pink-50/80', text: 'text-pink-950', border: 'border-pink-200' }, { id: 'lab', label: 'Lab / Academic', color: '#FDE047', bg: 'bg-yellow-50/80', text: 'text-yellow-950', border: 'border-yellow-200' }, { id: 'amenity', label: 'Amenity', color: '#BEF264', bg: 'bg-lime-50/80', text: 'text-lime-950', border: 'border-lime-200' }, { id: 'parking', label: 'Parking Area', color: '#94A3B8', bg: 'bg-slate-100/80', text: 'text-slate-900', border: 'border-slate-300' }, @@ -39,15 +40,15 @@ const LOCATION_SPOTS: LocationSpot[] = [ { name: 'Girls Mess', x: 14.5, y: 31.0, category: 'Hostel / Mess', desc: 'Dedicated Dining Hall for Women', area: 'West Wing' }, { name: 'MEC Lab', x: 14.0, y: 39.5, category: 'Lab / Academic', desc: 'Mechanical Engineering Laboratory', area: 'West Wing' }, { name: 'EPL Lab', x: 13.0, y: 47.5, category: 'Lab / Academic', desc: 'Engineering Practices Laboratory', area: 'West Wing' }, - { name: 'Nikola Tesla Block', x: 40.5, y: 36.5, category: 'B Block', desc: 'Main Electrical & Engineering Research Block', area: 'Central Block' }, + { name: 'B Block (Nikola Tesla Block)', x: 40.5, y: 36.5, category: 'B Block', desc: 'Main Electrical & Engineering Research Block', area: 'Central Block' }, { name: 'Astronaut Statue', x: 51.0, y: 23.0, category: 'Amenity', desc: 'Iconic Landmark Monument', area: 'Central Park' }, { name: 'Campus Centre', x: 67.0, y: 23.0, category: 'Admin / Facility', desc: 'Student Activity & Administrative Center', area: 'North East' }, { name: 'Hut', x: 70.0, y: 37.0, category: 'Amenity', desc: 'Student Discussion & Rest Area', area: 'Central East' }, - { name: 'Homi Jehangir Bhabha Block', x: 87.0, y: 24.0, category: 'A Block', desc: 'Science & Physics Research Block', area: 'East Wing' }, - { name: 'Boys Mess', x: 87.0, y: 17.5, category: 'Hostel / Mess', desc: 'Ground Floor Dining Hall for Men (Homi Bhabha Block)', area: 'East Wing' }, - { name: 'Staff Mess', x: 87.0, y: 30.5, category: 'Amenity', desc: 'First Floor Dining Hall for Faculty & Staff (Homi Bhabha Block)', area: 'East Wing' }, + { name: 'H Block (Homi Jehangir Bhabha Block)', x: 87.0, y: 24.0, category: 'H Block', desc: 'Science & Physics Research Block', area: 'East Wing' }, + { name: 'Boys Mess', x: 87.0, y: 17.5, category: 'Hostel / Mess', desc: 'Ground Floor Dining Hall for Men (H Block)', area: 'East Wing' }, + { name: 'Staff Mess', x: 87.0, y: 30.5, category: 'Amenity', desc: 'First Floor Dining Hall for Faculty & Staff (H Block)', area: 'East Wing' }, { name: 'C Block', x: 87.0, y: 38.0, category: 'C Block', desc: 'Labs, Classrooms & Staff Rooms', area: 'East Wing' }, - { name: 'Alan Turing Block', x: 77.0, y: 53.0, category: 'Lab / Academic', desc: 'Computer Science & AI Labs', area: 'East Wing' }, + { name: 'A Block (Alan Turing Block)', x: 77.0, y: 53.0, category: 'A Block', desc: 'Computer Science & AI Labs', area: 'East Wing' }, { name: 'Arcade', x: 35.0, y: 57.0, category: 'Amenity', desc: 'Student Hub & Stores', area: 'Central South' }, { name: 'Green Building', x: 23.0, y: 71.0, category: 'Admin / Facility', desc: 'Eco-Friendly Academic Complex & Library', area: 'South West' }, { name: 'Security Booth', x: 49.0, y: 77.0, category: 'Amenity', desc: 'Main Gate Security Checkpoint', area: 'South Entrance' }, @@ -59,9 +60,9 @@ const LOCATION_SPOTS: LocationSpot[] = [ ]; const CATEGORY_MAP_SPOTS: Record = { - dept: ['Homi Jehangir Bhabha Block', 'Nikola Tesla Block', 'C Block', 'Steve Jobs Block', 'Alan Turing Block', 'Green Building'], + dept: ['A Block (Alan Turing Block)', 'B Block (Nikola Tesla Block)', 'C Block', 'H Block (Homi Jehangir Bhabha Block)', 'Steve Jobs Block', 'Green Building'], library: ['Green Building'], - labs: ['MEC Lab', 'EPL Lab', 'Steve Jobs Block', 'Alan Turing Block', 'Nikola Tesla Block', 'C Block'], + labs: ['MEC Lab', 'EPL Lab', 'A Block (Alan Turing Block)', 'B Block (Nikola Tesla Block)', 'C Block', 'H Block (Homi Jehangir Bhabha Block)', 'Steve Jobs Block'], hostel: ['Girls Hostel', 'Boys Mess'], canteen: ['Canteen', 'Girls Mess', 'Boys Mess', 'Staff Mess', 'Arcade'], auditorium: ['Steve Jobs Block', 'Campus Centre'], @@ -119,6 +120,7 @@ export default function Campus() { if (activeLegend === 'a-block' && spot.category === 'A Block') highlightedSpotNames.add(spot.name); if (activeLegend === 'b-block' && spot.category === 'B Block') highlightedSpotNames.add(spot.name); if (activeLegend === 'c-block' && spot.category === 'C Block') highlightedSpotNames.add(spot.name); + if (activeLegend === 'h-block' && spot.category === 'H Block') highlightedSpotNames.add(spot.name); if (activeLegend === 'admin' && spot.category === 'Admin / Facility') highlightedSpotNames.add(spot.name); if (activeLegend === 'hostel' && spot.category === 'Hostel / Mess') highlightedSpotNames.add(spot.name); if (activeLegend === 'lab' && spot.category === 'Lab / Academic') highlightedSpotNames.add(spot.name); @@ -133,6 +135,7 @@ export default function Campus() { if (activeLegend === 'a-block') return fac.category === 'A Block'; if (activeLegend === 'b-block') return fac.category === 'B Block'; if (activeLegend === 'c-block') return fac.category === 'C Block'; + if (activeLegend === 'h-block') return fac.category === 'H Block'; if (activeLegend === 'admin') return fac.category === 'Admin / Facility'; if (activeLegend === 'hostel') return fac.category === 'Hostel / Mess'; if (activeLegend === 'lab') return fac.category === 'Lab / Academic'; From 38a64783d31cc6398163c70daafd5a8a3afddf02 Mon Sep 17 00:00:00 2001 From: Devesh S Date: Fri, 7 Aug 2026 14:47:05 +0530 Subject: [PATCH 11/11] separate Toolkit into standalone page and route --- src/App.tsx | 2 + src/constants/index.ts | 2 +- src/pages/Notes/Notes.tsx | 52 -- src/pages/Toolkit/Toolkit.tsx | 1020 +++++++++++++++++++++++++++++++++ 4 files changed, 1023 insertions(+), 53 deletions(-) create mode 100644 src/pages/Toolkit/Toolkit.tsx diff --git a/src/App.tsx b/src/App.tsx index 19058ff..4bd0292 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -6,6 +6,7 @@ import ProtectedRoute from '@/components/Auth/ProtectedRoute'; import MainLayout from '@/layouts/MainLayout'; import Home from '@/pages/Home/Home'; import Notes from '@/pages/Notes/Notes'; +import Toolkit from '@/pages/Toolkit/Toolkit'; import AIAssistant from '@/pages/AIAssistant/AIAssistant'; import Campus from '@/pages/Campus/Campus'; import Events from '@/pages/Events/Events'; @@ -44,6 +45,7 @@ function App() { }> } /> } /> + } /> } /> } /> } /> diff --git a/src/constants/index.ts b/src/constants/index.ts index 34f9b46..3424b18 100644 --- a/src/constants/index.ts +++ b/src/constants/index.ts @@ -94,7 +94,7 @@ export const FEATURES: Feature[] = [ icon: 'Wrench', title: 'Student Toolkit', description: 'Download timetables, academic calendar, syllabus, forms, and ERP guides.', - path: '/notes?section=toolkit', + path: '/toolkit', color: '#06B6D4', bgColor: '#ECFEFF', }, diff --git a/src/pages/Notes/Notes.tsx b/src/pages/Notes/Notes.tsx index 7e48e37..8b4ccd1 100644 --- a/src/pages/Notes/Notes.tsx +++ b/src/pages/Notes/Notes.tsx @@ -2025,58 +2025,6 @@ export default function Notes() {
- - {/* Toolkit Section */} -
- - - {TOOLKIT_ITEMS.map((item) => { - const iconConfig = TOOLKIT_ICONS[item.title] || { icon: Code, bg: '#FFF7ED', color: '#F97316' }; - const IconComponent = iconConfig.icon; - return ( - - { - if (item.title === 'CS tools') { - setSelectedToolkit('cs'); - } else if (item.title === 'Business tools') { - setSelectedToolkit('business'); - } else if (item.title === 'Electrical and Electronic tools') { - setSelectedToolkit('electrical'); - } else if (item.title === 'Cybersecurity tools') { - setSelectedToolkit('cybersecurity'); - } else if (item.title === 'AI tools') { - setSelectedToolkit('ai'); - } else if (item.title === 'Biotech tools') { - setSelectedToolkit('biotech'); - } else if (item.url && item.url !== '#') { - window.open(item.url, '_blank'); - } - }} - whileHover={{ y: -4, boxShadow: '0 12px 30px -10px rgba(249,115,22,0.15)' }} - className="flex items-start gap-5 p-7 bg-white hover:bg-[#FFF7ED] rounded-[22px] border border-[#E5E7EB] hover:border-[#FED7AA] cursor-pointer group w-full transition-all shadow-xs hover:shadow-md" - > -
- -
-
-
- {item.title} -
-
- {item.description} -
-
- -
-
- ); - })} -
-
)}
diff --git a/src/pages/Toolkit/Toolkit.tsx b/src/pages/Toolkit/Toolkit.tsx new file mode 100644 index 0000000..e7a03d3 --- /dev/null +++ b/src/pages/Toolkit/Toolkit.tsx @@ -0,0 +1,1020 @@ +import { useState, useRef, useEffect } from 'react'; +import { useSearchParams, Link } from 'react-router-dom'; +import { motion } from 'framer-motion'; +import { + Search, Download, BookOpen, ChevronRight, ArrowLeft, ExternalLink, Code, Globe, + GitBranch, Cloud, Palette, Shield, DollarSign, BarChart3, Users, Megaphone, + TrendingUp, UserCheck, ClipboardList, ShoppingCart, Cpu, Activity, LayoutGrid, + Layers, Zap, Settings, Gauge, Radio, Wifi, Bot, Sun, Wrench, Binary, BatteryCharging, + CircuitBoard, ShieldCheck, BrainCircuit, FlaskConical, Lock, Terminal, Dna, Microscope, + Sparkles, Smartphone, Monitor, Server, CheckCircle2, Database, Briefcase, AlertTriangle, RefreshCw +} from 'lucide-react'; +import SectionTitle from '@/components/SectionTitle/SectionTitle'; +import { StaggerContainer, StaggerItem } from '@/components/AnimatedContainer/AnimatedContainer'; +import { TOOLKIT_ITEMS } from '@/constants'; + +const TOOLKIT_ICONS: Record; bg: string; color: string }> = { + 'CS tools': { icon: Code, bg: '#EFF6FF', color: '#3B82F6' }, + 'Business tools': { icon: Briefcase, bg: '#ECFDF5', color: '#10B981' }, + 'Cybersecurity tools': { icon: ShieldCheck, bg: '#F5F3FF', color: '#8B5CF6' }, + 'AI tools': { icon: BrainCircuit, bg: '#FDF2F8', color: '#EC4899' }, + 'Electrical and Electronic tools': { icon: Zap, bg: '#FEF3C7', color: '#D97706' }, + 'Biotech tools': { icon: Dna, bg: '#ECFEFF', color: '#06B6D4' }, +}; + +const PROGRAMMING_LANGUAGES_GUIDES = [ + { + name: 'Python', + tagline: 'Simple, Readable & Beginner-Friendly', + color: '#3776AB', + bg: '#EFF6FF', + whatItIs: 'Python is known for its clean, English-like syntax. It lets you write code quickly without worrying about complex computer memory setups, making it the top choice for beginners.', + keyConcepts: [ + 'Writing your first line of code using print("Hello World!")', + 'Storing numbers, text, and lists in smart variables', + 'Making decisions in code using simple if and else conditions', + 'Automating repetitive tasks effortlessly using loops', + 'Reusing code blocks with custom functions (def)', + 'Using pre-built libraries to build web apps, AI bots, or scrape web data' + ], + useCases: ['Web Development (Django, FastAPI)', 'Data Science & Analytics', 'Artificial Intelligence & Machine Learning', 'Automation & Web Scraping'], + links: [ + { label: 'Official Python Documentation', url: 'https://docs.python.org/3/' }, + { label: 'Python for Beginners Guide', url: 'https://www.python.org/about/gettingstarted/' }, + { label: 'FreeCodeCamp Python Course', url: 'https://www.freecodecamp.org/news/learn-python-free-python-courses-for-beginners/' } + ] + }, + { + name: 'Java', + tagline: 'Build Once, Run Anywhere', + color: '#007396', + bg: '#E0F2FE', + whatItIs: 'Java powers enterprise apps, banking systems, and Android smartphones. Code written in Java can run on any operating system without modification!', + keyConcepts: [ + 'Understanding Classes & Objects — modeling real-world items in code', + 'Learning how the main() method serves as the starting trigger', + 'Organizing data cleanly using static types like int, String, and boolean', + 'Reusing existing code seamlessly with Inheritance & Interfaces', + 'Handling errors gracefully so applications never crash unexpectedly', + 'Building robust backend services with Spring Boot' + ], + useCases: ['Enterprise Backend Systems', 'Android Application Development', 'Financial & Banking Systems', 'Large-Scale Web Services'], + links: [ + { label: 'Official Oracle Java Docs', url: 'https://docs.oracle.com/en/java/' }, + { label: 'W3Schools Java Tutorial', url: 'https://www.w3schools.com/java/' }, + { label: 'Spring Boot Getting Started', url: 'https://spring.io/guides' } + ] + }, + { + name: 'C++', + tagline: 'Blazing Speed & Hardware Control', + color: '#00599C', + bg: '#EFF6FF', + whatItIs: 'C++ provides ultimate control over memory and hardware. It is the core language powering high-end video games, operating systems, and flight controllers.', + keyConcepts: [ + 'Compiling human-readable code into ultra-fast machine instructions', + 'Exploring Pointers (*) & Memory Addresses (&) for direct hardware control', + 'Using the Standard Template Library (STL) for instant stacks, queues, and vectors', + 'Structuring programs cleanly with Classes, Structs, and Objects', + 'Solving complex algorithmic puzzles in competitive programming', + 'Building 3D game engines like Unreal Engine' + ], + useCases: ['Game Engines (Unreal Engine)', 'Operating Systems & Browsers', 'Competitive Programming & DSA', 'Embedded Systems & Robotics'], + links: [ + { label: 'cppreference.com Reference', url: 'https://en.cppreference.com/' }, + { label: 'LearnCpp Free Tutorials', url: 'https://www.learncpp.com/' }, + { label: 'GeeksforGeeks C++ Programming', url: 'https://www.geeksforgeeks.org/c-plus-plus/' } + ] + }, + { + name: 'JavaScript', + tagline: 'The Heartbeat of the Web', + color: '#D97706', + bg: '#FEFCE8', + whatItIs: 'JavaScript brings websites to life! Every button click, popup animation, dynamic page update, and live chat on the web is powered by JavaScript.', + keyConcepts: [ + 'Making web pages interactive by responding to user clicks and keypresses', + 'Changing text, colors, and layouts dynamically on the screen (DOM)', + 'Fetching live data from servers without refreshing the browser (fetch API)', + 'Writing clean code using modern Arrow Functions (() => {})', + 'Handling background actions smoothly using async / await', + 'Building backend web servers using Node.js' + ], + useCases: ['Interactive Web Interfaces (React, Vue)', 'Backend Web Servers (Node.js)', 'Full-Stack Web Applications', 'Mobile Apps (React Native)'], + links: [ + { label: 'MDN JavaScript Documentation', url: 'https://developer.mozilla.org/en-US/docs/Web/JavaScript' }, + { label: 'JavaScript.info Modern Tutorial', url: 'https://javascript.info/' }, + { label: 'W3Schools JavaScript Guide', url: 'https://www.w3schools.com/js/' } + ] + }, + { + name: 'TypeScript', + tagline: 'JavaScript with Smart Safety Nets', + color: '#3178C6', + bg: '#EFF6FF', + whatItIs: 'TypeScript is JavaScript with built-in type checking! It acts like an intelligent spell-checker for code, preventing bugs and typos before your app even launches.', + keyConcepts: [ + 'Adding clear types (string, number) to catch bugs as you type', + 'Creating Interfaces to define exact data structures for your app', + 'Enjoying supercharged code suggestions & autocomplete in VS Code', + 'Building scalable React and Next.js web applications', + 'Catching errors during development instead of in production' + ], + useCases: ['Enterprise Web Applications', 'Modern React & Next.js Apps', 'Scalable Microservices', 'Large-Scale Team Projects'], + links: [ + { label: 'Official TypeScript Handbook', url: 'https://www.typescriptlang.org/docs/handbook/intro.html' }, + { label: 'TypeScript in 5 Minutes', url: 'https://www.typescriptlang.org/docs/handbook/typescript-in-5-minutes.html' } + ] + }, + { + name: 'Go (Golang)', + tagline: 'Built by Google for Cloud Speed', + color: '#00ADD8', + bg: '#ECFEFF', + whatItIs: 'Created at Google for simplicity and lightning speed. Go is famous for powering modern cloud infrastructure like Docker and Kubernetes.', + keyConcepts: [ + 'Writing simple, ultra-clean code without unnecessary syntax clutter', + 'Running thousands of background tasks at once using Goroutines', + 'Passing data safely between parallel tasks using Channels', + 'Building super-fast Web APIs in just a few lines of code', + 'Compiling your entire project into a single fast binary executable' + ], + useCases: ['Cloud Platforms (Docker, Kubernetes)', 'High-Speed Microservices', 'DevOps Tools', 'Network Infrastructure'], + links: [ + { label: 'A Tour of Go (Interactive)', url: 'https://go.dev/tour/' }, + { label: 'Official Go Documentation', url: 'https://go.dev/doc/' } + ] + }, + { + name: 'Rust', + tagline: 'Maximum Speed Without System Crashes', + color: '#CE412B', + bg: '#FFF7ED', + whatItIs: 'Rust gives you the speed of C++ with memory safety. It guarantees that software will not crash due to memory leaks or unexpected buffer glitches.', + keyConcepts: [ + 'Understanding Ownership — how Rust automatically manages memory', + 'Sharing data safely across code using Borrowing (&)', + 'Handling all possible conditions cleanly with pattern matching (match)', + 'Managing packages, builds, and tests using the Cargo tool', + 'Building high-security web servers, crypto engines, and WebAssembly apps' + ], + useCases: ['Systems & Kernel Development', 'WebAssembly (Wasm) Applications', 'High-Performance Networking', 'Blockchain & Security Engines'], + links: [ + { label: 'The Rust Programming Language Book', url: 'https://doc.rust-lang.org/book/' }, + { label: 'Rust by Example', url: 'https://doc.rust-lang.org/rust-by-example/' } + ] + }, + { + name: 'C# (.NET)', + tagline: 'Modern, Versatile & Game-Ready', + color: '#239120', + bg: '#ECFDF5', + whatItIs: 'Created by Microsoft, C# is an elegant language widely used for building 3D/2D games in Unity, Windows desktop applications, and web services.', + keyConcepts: [ + 'Writing clean Object-Oriented code with concise Properties', + 'Filtering, searching, and sorting data in 1 line using LINQ', + 'Building immersive video games with the Unity Game Engine', + 'Creating high-speed web APIs using ASP.NET Core', + 'Building cross-platform desktop & mobile apps with .NET MAUI' + ], + useCases: ['Unity 3D/2D Game Development', 'Enterprise Web Backends (ASP.NET Core)', 'Windows Desktop Applications', 'Cross-Platform Apps (.NET MAUI)'], + links: [ + { label: 'Official Microsoft C# Documentation', url: 'https://learn.microsoft.com/en-us/dotnet/csharp/' }, + { label: 'W3Schools C# Guide', url: 'https://www.w3schools.com/cs/' } + ] + } +]; + +const CS_TOOLS_CATEGORIES = [ + { + title: 'Programming Languages', + icon: Code, + color: '#3B82F6', + bg: '#EFF6FF', + tools: [ + { name: 'Python', desc: 'High-level, beginner-friendly language for AI, Web, & Scripts.', url: '#' }, + { name: 'Java', desc: 'Object-oriented enterprise language running on the JVM.', url: '#' }, + { name: 'C++', desc: 'High-performance systems programming and game development.', url: '#' }, + { name: 'JavaScript', desc: 'Core language of the web for frontend and backend.', url: '#' }, + { name: 'TypeScript', desc: 'Strongly typed superset of JavaScript at scale.', url: '#' }, + { name: 'Go (Golang)', desc: 'Fast, concurrent language for cloud & microservices.', url: '#' }, + { name: 'Rust', desc: 'Ultra-fast memory-safe systems programming language.', url: '#' }, + { name: 'C# (.NET)', desc: 'Versatile OOP language for games, desktop, & web backends.', url: '#' } + ] + }, + { + title: 'Version Control', + icon: GitBranch, + color: '#F97316', + bg: '#FFF7ED', + tools: [ + { name: 'Source Code Management', desc: 'Git CLI distributed version control system.', url: 'https://git-scm.com/' }, + { name: 'Repository Hosting', desc: 'GitHub, GitLab, Bitbucket, and Gitea platforms.', url: 'https://github.com/' }, + { name: 'Git Clients', desc: 'GitHub Desktop, GitKraken, Sourcetree, and Lazygit.', url: 'https://desktop.github.com/' }, + { name: 'Code Review', desc: 'GitHub Pull Requests, Crucible, and Gerrit review workflows.', url: 'https://github.com/features/code-review' } + ] + }, + { + title: 'Web Development', + icon: Globe, + color: '#10B981', + bg: '#ECFDF5', + tools: [ + { name: 'Frontend Development', desc: 'React, Vue.js, Angular, Svelte, Tailwind CSS, HTML5/CSS3.', url: 'https://react.dev/' }, + { name: 'Backend Development', desc: 'Spring Boot, Express.js, Django, FastAPI, NestJS.', url: 'https://spring.io/projects/spring-boot' }, + { name: 'Full-Stack Development', desc: 'Next.js, Remix, Nuxt.js, and Astro full-stack frameworks.', url: 'https://nextjs.org/' }, + { name: 'Static Site Generators', desc: 'Gatsby, Hugo, Jekyll, and Eleventy.', url: 'https://www.gatsbyjs.com/' }, + { name: 'CMS', desc: 'WordPress, Strapi, Sanity, and Ghost Content Management Systems.', url: 'https://strapi.io/' }, + { name: 'Web Performance', desc: 'Lighthouse, PageSpeed Insights, and Web Vitals analytics.', url: 'https://pagespeed.web.dev/' } + ] + }, + { + title: 'Mobile Development', + icon: Smartphone, + color: '#8B5CF6', + bg: '#F5F3FF', + tools: [ + { name: 'Android Development', desc: 'Android Studio, Kotlin, Jetpack Compose, and Java.', url: 'https://developer.android.com/studio' }, + { name: 'iOS Development', desc: 'Xcode, Swift, SwiftUI, and CocoaPods.', url: 'https://developer.apple.com/xcode/' }, + { name: 'Cross-Platform Development', desc: 'Flutter, React Native, and Expo framework.', url: 'https://flutter.dev/' }, + { name: 'Mobile Testing', desc: 'Appium, Espresso, and XCUITest automation.', url: 'https://appium.io/' }, + { name: 'App Deployment', desc: 'Google Play Console, Apple App Store Connect, Fastlane.', url: 'https://play.google.com/console' } + ] + }, + { + title: 'Databases', + icon: Database, + color: '#06B6D4', + bg: '#ECFEFF', + tools: [ + { name: 'Relational Databases (SQL)', desc: 'PostgreSQL, MySQL, SQLite, and Microsoft SQL Server.', url: 'https://www.postgresql.org/' }, + { name: 'NoSQL Databases', desc: 'MongoDB, Cassandra, CouchDB, and DynamoDB.', url: 'https://www.mongodb.com/' }, + { name: 'Graph Databases', desc: 'Neo4j, Amazon Neptune, and ArangoDB.', url: 'https://neo4j.com/' }, + { name: 'Time-Series Databases', desc: 'InfluxDB, TimescaleDB, and Prometheus.', url: 'https://www.influxdata.com/' }, + { name: 'In-Memory Databases', desc: 'Redis, Memcached, and Dragonfly.', url: 'https://redis.io/' }, + { name: 'Database Administration', desc: 'pgAdmin, DBeaver, DataGrip, and phpMyAdmin.', url: 'https://www.dbeaver.io/' }, + { name: 'Database Modeling', desc: 'dbdiagram.io, Erwin, and MySQL Workbench.', url: 'https://dbdiagram.io/' } + ] + }, + { + title: 'UI / UX Design', + icon: Palette, + color: '#EC4899', + bg: '#FDF2F8', + tools: [ + { name: 'Wireframing', desc: 'Balsamiq, Figma, and Whimsical wireframing.', url: 'https://balsamiq.com/' }, + { name: 'Prototyping', desc: 'Figma, Adobe XD, Proto.io, and Framer.', url: 'https://www.figma.com/' }, + { name: 'Design Systems', desc: 'Storybook, Material Design, and Tailwind UI.', url: 'https://storybook.js.org/' }, + { name: 'User Research', desc: 'Maze, UserTesting, and Hotjar analytics.', url: 'https://maze.co/' }, + { name: 'Accessibility Testing', desc: 'axe DevTools, WAVE, and Lighthouse A11y audit.', url: 'https://www.deque.com/axe/' } + ] + }, + { + title: 'Collaboration', + icon: Users, + color: '#EAB308', + bg: '#FEFCE8', + tools: [ + { name: 'Documentation', desc: 'Confluence, Notion, MkDocs, and Docusaurus.', url: 'https://docusaurus.io/' }, + { name: 'Team Communication', desc: 'Slack, Microsoft Teams, Discord, and Mattermost.', url: 'https://slack.com/' }, + { name: 'Project Management', desc: 'Jira, Trello, Asana, and Linear ticket tracking.', url: 'https://linear.app/' }, + { name: 'Whiteboarding', desc: 'Miro, FigJam, Excalidraw, and Lucidchart.', url: 'https://excalidraw.com/' }, + { name: 'Knowledge Management', desc: 'Obsidian, Notion, and Slite workspace wiki.', url: 'https://obsidian.md/' } + ] + }, + { + title: 'Software Engineering', + icon: Layers, + color: '#D97706', + bg: '#FEF3C7', + tools: [ + { name: 'UML & System Design', desc: 'Draw.io, PlantUML, Mermaid.js, and StarUML.', url: 'https://mermaid.js.org/' }, + { name: 'Architecture Design', desc: 'C4 Model, ArchiMate, and System Architecture patterns.', url: 'https://c4model.com/' }, + { name: 'Design Patterns', desc: 'Gang of Four (GoF) Creational, Structural, Behavioral patterns.', url: 'https://refactoring.guru/design-patterns' }, + { name: 'Code Analysis', desc: 'SonarQube, ESLint, Pylint, and SpotBugs linters.', url: 'https://eslint.org/' }, + { name: 'Debugging', desc: 'GDB, Chrome DevTools, Visual Studio Debugger, and Charles Proxy.', url: 'https://developer.chrome.com/docs/devtools/' }, + { name: 'Performance Profiling', desc: 'Perf, JProfiler, Py-Spy, and Chrome Memory Profiler.', url: 'https://github.com/benfred/py-spy' } + ] + }, + { + title: 'Networking', + icon: Wifi, + color: '#2563EB', + bg: '#EFF6FF', + tools: [ + { name: 'Network Analysis', desc: 'Wireshark packet capture and traffic protocol analyzer.', url: 'https://www.wireshark.org/' }, + { name: 'Packet Simulation', desc: 'Cisco Packet Tracer and GNS3 network topology simulation.', url: 'https://www.netacad.com/courses/packet-tracer' }, + { name: 'Port Scanning & Recon', desc: 'Nmap and Masscan network discovery tools.', url: 'https://nmap.org/' }, + { name: 'API & HTTP Debugging', desc: 'Postman, Fiddler, and Charles Proxy HTTP inspection.', url: 'https://www.postman.com/' }, + { name: 'Remote Terminal & SSH', desc: 'PuTTY, OpenSSH, and Termius terminal clients.', url: 'https://www.putty.org/' } + ] + } +]; + +const BUSINESS_TOOLS_CATEGORIES = [ + { + title: 'Accounting & Finance', + icon: DollarSign, + color: '#10B981', + bg: '#ECFDF5', + tools: [ + { name: 'QuickBooks', desc: 'Cloud accounting software for small and mid-sized businesses.', url: 'https://quickbooks.intuit.com/' }, + { name: 'Tally Prime', desc: 'India\'s leading accounting and inventory management solution.', url: 'https://tallysolutions.com/' }, + { name: 'Zoho Books', desc: 'Online accounting software for growing businesses.', url: 'https://www.zoho.com/books/' } + ] + }, + { + title: 'Business Intelligence', + icon: BarChart3, + color: '#3B82F6', + bg: '#EFF6FF', + tools: [ + { name: 'Power BI', desc: 'Microsoft\'s interactive data visualization and BI tool.', url: 'https://powerbi.microsoft.com/' }, + { name: 'Tableau', desc: 'Visual analytics platform for data-driven decisions.', url: 'https://www.tableau.com/' }, + { name: 'Google Looker', desc: 'Business intelligence and data analytics by Google Cloud.', url: 'https://cloud.google.com/looker' } + ] + }, + { + title: 'CRM', + icon: Users, + color: '#8B5CF6', + bg: '#F5F3FF', + tools: [ + { name: 'Salesforce', desc: 'World\'s leading CRM platform for sales and support.', url: 'https://www.salesforce.com/' }, + { name: 'HubSpot CRM', desc: 'Free CRM with marketing, sales, and service tools.', url: 'https://www.hubspot.com/products/crm' }, + { name: 'Zoho CRM', desc: 'AI-powered CRM for customer lifecycle management.', url: 'https://www.zoho.com/crm/' } + ] + }, + { + title: 'Marketing', + icon: Megaphone, + color: '#EC4899', + bg: '#FDF2F8', + tools: [ + { name: 'Google Ads', desc: 'Online advertising platform for paid search and display.', url: 'https://ads.google.com/' }, + { name: 'Mailchimp', desc: 'Email marketing and automation platform.', url: 'https://mailchimp.com/' }, + { name: 'Canva', desc: 'Design tool for social media graphics and presentations.', url: 'https://www.canva.com/' } + ] + }, + { + title: 'Sales', + icon: TrendingUp, + color: '#F97316', + bg: '#FFF7ED', + tools: [ + { name: 'LinkedIn Sales Navigator', desc: 'Advanced lead generation and prospecting tool.', url: 'https://business.linkedin.com/sales-solutions' }, + { name: 'Pipedrive', desc: 'Sales CRM and pipeline management tool.', url: 'https://www.pipedrive.com/' }, + { name: 'Freshsales', desc: 'AI-powered sales CRM for high-velocity teams.', url: 'https://www.freshworks.com/crm/sales/' } + ] + }, + { + title: 'Human Resources (HR)', + icon: UserCheck, + color: '#06B6D4', + bg: '#ECFEFF', + tools: [ + { name: 'BambooHR', desc: 'HR software for employee records, onboarding, and PTO.', url: 'https://www.bamboohr.com/' }, + { name: 'Workday', desc: 'Enterprise cloud platform for finance, HR, and planning.', url: 'https://www.workday.com/' }, + { name: 'Zoho People', desc: 'Cloud HRMS software for managing employee operations.', url: 'https://www.zoho.com/people/' } + ] + }, + { + title: 'Project & Operations', + icon: ClipboardList, + color: '#D97706', + bg: '#FEF3C7', + tools: [ + { name: 'Asana', desc: 'Work management platform to organize team projects.', url: 'https://asana.com/' }, + { name: 'Trello', desc: 'Kanban-style project management and list tool.', url: 'https://trello.com/' }, + { name: 'Smartsheet', desc: 'Enterprise platform for dynamic work and project management.', url: 'https://www.smartsheet.com/' } + ] + }, + { + title: 'E-Commerce', + icon: ShoppingCart, + color: '#6366F1', + bg: '#EEF2FF', + tools: [ + { name: 'Shopify', desc: 'E-commerce platform for online stores and retail POS.', url: 'https://www.shopify.com/' }, + { name: 'WooCommerce', desc: 'Open-source e-commerce plugin for WordPress.', url: 'https://woocommerce.com/' }, + { name: 'Magento (Adobe Commerce)', desc: 'Flexible enterprise e-commerce platform.', url: 'https://business.adobe.com/products/magento/magento-commerce.html' } + ] + } +]; + +const EE_TOOLS_CATEGORIES = [ + { + title: 'Circuit Simulation & CAD', + icon: Cpu, + color: '#D97706', + bg: '#FEF3C7', + tools: [ + { name: 'LTspice', desc: 'High-performance SPICE simulation software for analog circuits.', url: 'https://www.analog.com/en/design-center/design-tools-and-calculators/ltspice-simulator.html' }, + { name: 'Proteus Design Suite', desc: 'Circuit simulation, schematic capture, and PCB layout.', url: 'https://www.labcenter.com/' }, + { name: 'Multisim (NI)', desc: 'SPICE simulation and circuit design environment.', url: 'https://www.ni.com/en-in/shop/electronic-test-instrumentation/application-software-for-electronic-test-and-instrumentation-category/what-is-multisim.html' } + ] + }, + { + title: 'Computation & Analysis', + icon: Activity, + color: '#0284C7', + bg: '#E0F2FE', + tools: [ + { name: 'MATLAB', desc: 'Numerical computing environment for algorithms and data analysis.', url: 'https://www.mathworks.com/products/matlab.html' }, + { name: 'Simulink', desc: 'Block diagram environment for multi-domain simulation.', url: 'https://www.mathworks.com/products/simulink.html' }, + { name: 'LabVIEW', desc: 'System design software for test, measurement, and control.', url: 'https://www.ni.com/en-in/shop/labview.html' } + ] + }, + { + title: 'PCB Design', + icon: LayoutGrid, + color: '#16A34A', + bg: '#DCFCE7', + tools: [ + { name: 'KiCad EDA', desc: 'Open-source electronics design automation suite.', url: 'https://www.kicad.org/' }, + { name: 'Altium Designer', desc: 'PCB design and electronics development software.', url: 'https://www.altium.com/' }, + { name: 'Eagle (Autodesk)', desc: 'PCB layout and schematic editing software.', url: 'https://www.autodesk.com/products/eagle/overview' } + ] + }, + { + title: 'Embedded Systems', + icon: Layers, + color: '#7C3AED', + bg: '#F3E8FF', + tools: [ + { name: 'STM32CubeIDE', desc: 'C/C++ development platform for STM32 microcontrollers.', url: 'https://www.st.com/en/development-tools/stm32cubeide.html' }, + { name: 'Keil uVision', desc: 'IDE for ARM cortex microcontroller programming.', url: 'https://www.keil.com/' }, + { name: 'Arduino IDE', desc: 'Open-source software for microcontroller board programming.', url: 'https://www.arduino.cc/en/software' } + ] + }, + { + title: 'Power Systems', + icon: Zap, + color: '#EA580C', + bg: '#FFEDD5', + tools: [ + { name: 'ETAP', desc: 'Electrical power system analysis and operation software.', url: 'https://etap.com/' }, + { name: 'PSCAD', desc: 'Power system transient simulation environment.', url: 'https://www.pscad.com/' }, + { name: 'PowerWorld Simulator', desc: 'Power system visual analysis and power flow tool.', url: 'https://www.powerworld.com/' } + ] + }, + { + title: 'Control Systems', + icon: Settings, + color: '#059669', + bg: '#D1FAE5', + tools: [ + { name: 'Control System Toolbox (MATLAB)', desc: 'Tools for analyzing and designing control systems.', url: 'https://www.mathworks.com/products/control.html' }, + { name: 'Scilab Xcos', desc: 'Open-source graphical editor for dynamic systems simulation.', url: 'https://www.scilab.org/' } + ] + }, + { + title: 'Instrumentation', + icon: Gauge, + color: '#4F46E5', + bg: '#EEF2FF', + tools: [ + { name: 'NI MAX (Measurement & Automation Explorer)', desc: 'Configuration tool for NI hardware devices.', url: 'https://www.ni.com/' }, + { name: 'Keysight PathWave', desc: 'Test and measurement software suite.', url: 'https://www.keysight.com/' } + ] + }, + { + title: 'Signal Processing', + icon: Radio, + color: '#DB2777', + bg: '#FCE7F3', + tools: [ + { name: 'GNU Radio', desc: 'Software development toolkit for signal processing & SDR.', url: 'https://www.gnuradio.org/' }, + { name: 'DSP System Toolbox (MATLAB)', desc: 'Design and simulate signal processing systems.', url: 'https://www.mathworks.com/products/dsp-system.html' } + ] + } +]; + +const CYBERSECURITY_TOOLS_CATEGORIES = [ + { + title: 'Network Scanner', + icon: Wifi, + color: '#3B82F6', + bg: '#EFF6FF', + tools: [ + { name: 'Nmap', desc: 'Network discovery and vulnerability scanning security auditor.', url: 'https://nmap.org/' }, + { name: 'Masscan', desc: 'Ultra-fast IP port scanner capable of scanning the whole internet.', url: 'https://github.com/robertdavidgraham/masscan' }, + { name: 'Angry IP Scanner', desc: 'Fast and friendly network scanner for desktop platforms.', url: 'https://angryip.org/' } + ] + }, + { + title: 'Penetration Testing', + icon: ShieldCheck, + color: '#8B5CF6', + bg: '#F5F3FF', + tools: [ + { name: 'Metasploit Framework', desc: 'World\'s most used penetration testing framework.', url: 'https://www.metasploit.com/' }, + { name: 'Burp Suite', desc: 'Leading web security testing and vulnerability scanner.', url: 'https://portswigger.net/burp' }, + { name: 'OWASP ZAP', desc: 'Open-source web application security scanner.', url: 'https://www.zaproxy.org/' } + ] + }, + { + title: 'Forensics', + icon: Terminal, + color: '#06B6D4', + bg: '#ECFEFF', + tools: [ + { name: 'Autopsy', desc: 'Digital forensics platform and GUI for The Sleuth Kit.', url: 'https://www.autopsy.com/' }, + { name: 'Volatility', desc: 'Advanced memory forensics framework for incident response.', url: 'https://www.volatilityfoundation.org/' }, + { name: 'FTK Imager', desc: 'Data preview and forensic imaging tool.', url: 'https://www.exterro.com/ftk-imager' } + ] + }, + { + title: 'Cryptography', + icon: Lock, + color: '#EC4899', + bg: '#FDF2F8', + tools: [ + { name: 'OpenSSL', desc: 'Robust commercial-grade cryptography toolkit and SSL/TLS CLI.', url: 'https://www.openssl.org/' }, + { name: 'CyberChef', desc: 'The Cyber Swiss Army Knife for encryption, encoding, and data analysis.', url: 'https://gchq.github.io/CyberChef/' }, + { name: 'VeraCrypt', desc: 'Free open-source disk encryption software based on TrueCrypt.', url: 'https://www.veracrypt.fr/' } + ] + }, + { + title: 'Malware Analysis', + icon: Bot, + color: '#EF4444', + bg: '#FEF2F2', + tools: [ + { name: 'Ghidra', desc: 'NSA reverse engineering framework for software analysis.', url: 'https://ghidra-sre.org/' }, + { name: 'IDA Free', desc: 'Interactive disassembler for binary malware analysis.', url: 'https://hex-rays.com/ida-free/' }, + { name: 'Cuckoo Sandbox', desc: 'Automated malware analysis system.', url: 'https://cuckoosandbox.org/' } + ] + }, + { + title: 'Identity Management', + icon: UserCheck, + color: '#10B981', + bg: '#ECFDF5', + tools: [ + { name: 'HashiCorp Vault', desc: 'Manage secrets, keys, and credentials securely.', url: 'https://www.vaultproject.io/' }, + { name: 'Keycloak', desc: 'Open-source identity and access management for modern apps.', url: 'https://www.keycloak.org/' }, + { name: 'Okta', desc: 'Enterprise identity cloud platform for workforce authentication.', url: 'https://www.okta.com/' } + ] + } +]; + +const AI_TOOLS_CATEGORIES = [ + { + title: 'Machine Learning Frameworks', + icon: BrainCircuit, + color: '#EC4899', + bg: '#FDF2F8', + tools: [ + { name: 'PyTorch', desc: 'Leading open-source deep learning framework by Meta.', url: 'https://pytorch.org/' }, + { name: 'TensorFlow', desc: 'End-to-end open-source machine learning platform by Google.', url: 'https://www.tensorflow.org/' }, + { name: 'Scikit-Learn', desc: 'Simple and efficient tools for predictive data analysis in Python.', url: 'https://scikit-learn.org/' } + ] + }, + { + title: 'LLM & Generative AI', + icon: Bot, + color: '#8B5CF6', + bg: '#F5F3FF', + tools: [ + { name: 'Hugging Face Transformers', desc: 'Thousands of pretrained models for NLP, Vision, & Audio.', url: 'https://huggingface.co/' }, + { name: 'LangChain', desc: 'Framework for developing applications powered by language models.', url: 'https://www.langchain.com/' }, + { name: 'Ollama', desc: 'Run large language models locally on your machine.', url: 'https://ollama.com/' } + ] + }, + { + title: 'Computer Vision', + icon: Microscope, + color: '#3B82F6', + bg: '#EFF6FF', + tools: [ + { name: 'OpenCV', desc: 'Open-source computer vision and machine learning software library.', url: 'https://opencv.org/' }, + { name: 'YOLOv8 (Ultralytics)', desc: 'Real-time object detection and image segmentation.', url: 'https://www.ultralytics.com/' }, + { name: 'MediaPipe', desc: 'Cross-platform ML solutions for live and streaming media.', url: 'https://developers.google.com/mediapipe' } + ] + }, + { + title: 'Natural Language Processing (NLP)', + icon: Sparkles, + color: '#10B981', + bg: '#ECFDF5', + tools: [ + { name: 'spaCy', desc: 'Industrial-strength Natural Language Processing in Python.', url: 'https://spacy.io/' }, + { name: 'NLTK', desc: 'Natural Language Toolkit for symbolic and statistical NLP.', url: 'https://www.nltk.org/' }, + { name: 'Gensim', desc: 'Topic modeling and document similarity analysis for human language.', url: 'https://radimrehurek.com/gensim/' } + ] + }, + { + title: 'Data Annotation & MLOps', + icon: Database, + color: '#F97316', + bg: '#FFF7ED', + tools: [ + { name: 'MLflow', desc: 'Open-source platform to manage the ML lifecycle.', url: 'https://mlflow.org/' }, + { name: 'Label Studio', desc: 'Multi-type data labeling and annotation tool.', url: 'https://labelstud.io/' }, + { name: 'Weights & Biases (W&B)', desc: 'Developer platform for machine learning experiment tracking.', url: 'https://wandb.ai/' } + ] + } +]; + +const BIOTECH_TOOLS_CATEGORIES = [ + { + title: 'Bioinformatics & Sequence Analysis', + icon: Dna, + color: '#06B6D4', + bg: '#ECFEFF', + tools: [ + { name: 'NCBI BLAST', desc: 'Basic Local Alignment Search Tool for nucleotide & protein sequences.', url: 'https://blast.ncbi.nlm.nih.gov/Blast.cgi' }, + { name: 'Biopython', desc: 'Freely available Python tools for computational molecular biology.', url: 'https://biopython.org/' }, + { name: 'Clustal Omega', desc: 'Multiple sequence alignment program for DNA/RNA/protein.', url: 'https://www.ebi.ac.uk/Tools/msa/clustalo/' } + ] + }, + { + title: 'Molecular Modeling & Visualization', + icon: FlaskConical, + color: '#10B981', + bg: '#ECFDF5', + tools: [ + { name: 'PyMOL', desc: 'Molecular visualization system on an open-source foundation.', url: 'https://pymol.org/' }, + { name: 'UCSF ChimeraX', desc: 'Next-generation interactive molecular visualization and analysis.', url: 'https://www.rbvi.ucsf.edu/chimerax/' }, + { name: 'AutoDock Vina', desc: 'Molecular docking program for drug discovery and structural biology.', url: 'https://vina.scripps.edu/' } + ] + }, + { + title: 'Genomics & Next-Gen Sequencing', + icon: Microscope, + color: '#8B5CF6', + bg: '#F5F3FF', + tools: [ + { name: 'SAMtools', desc: 'Utilities for interacting with high-throughput sequencing data.', url: 'http://www.htslib.org/' }, + { name: 'FASTQC', desc: 'Quality control tool for high-throughput sequence data.', url: 'https://www.bioinformatics.babraham.ac.uk/projects/fastqc/' }, + { name: 'IGV (Integrative Genomics Viewer)', desc: 'High-performance interactive visualization tool for genomic data.', url: 'https://igv.org/' } + ] + } +]; + +export default function Toolkit() { + const [searchParams, setSearchParams] = useSearchParams(); + const selectedToolkit = searchParams.get('toolkit'); + const [selectedCategory, setSelectedCategory] = useState(null); + const [selectedLanguage, setSelectedLanguage] = useState(null); + const [selectedTool, setSelectedTool] = useState<{ name: string; desc: string; url: string; category: string; bg: string; color: string } | null>(null); + + const setSelectedToolkit = (value: string | null) => { + if (value) { + setSearchParams({ toolkit: value }); + setSelectedCategory(null); + setSelectedLanguage(null); + setSelectedTool(null); + } else { + setSearchParams({}); + setSelectedCategory(null); + setSelectedLanguage(null); + setSelectedTool(null); + } + }; + + const toolkitRef = useRef(null); + + return ( +
+ {/* Header */} + {!selectedToolkit && ( +
+
+ +
+ Home + + Student Toolkit +
+

+ Student{' '} + + Toolkit + +

+

+ Access specialized development environments, IDE configurations, compiler guides, and department toolkits. +

+
+
+
+ )} + +
+ {selectedToolkit ? ( + (() => { + const TOOLKIT_MAP: Record = { + cs: { categories: CS_TOOLS_CATEGORIES, label: 'Computer Science' }, + business: { categories: BUSINESS_TOOLS_CATEGORIES, label: 'Business' }, + electrical: { categories: EE_TOOLS_CATEGORIES, label: 'Electrical & Electronics' }, + cybersecurity: { categories: CYBERSECURITY_TOOLS_CATEGORIES, label: 'Cybersecurity' }, + ai: { categories: AI_TOOLS_CATEGORIES, label: 'Artificial Intelligence' }, + biotech: { categories: BIOTECH_TOOLS_CATEGORIES, label: 'Biotechnology' }, + }; + const current = TOOLKIT_MAP[selectedToolkit]; + if (!current) return null; + const { categories, label } = current; + return ( +
+ {/* Back Button and Title */} + + +
+

+ {label} Toolkit +

+
+

+ {selectedLanguage !== null + ? `Complete beginner guide, core concepts, use cases, and resources for ${PROGRAMMING_LANGUAGES_GUIDES[selectedLanguage].name}.` + : selectedCategory !== null + ? `Browse essential ${categories[selectedCategory].title} software, guides, and developer resources.` + : `Explore all categories and tools curated for ${label} students.`} +

+
+ + {/* Main Content Area */} + {selectedLanguage !== null ? ( + /* ── Detailed Programming Language Guide View ── */ + (() => { + const guide = PROGRAMMING_LANGUAGES_GUIDES[selectedLanguage]; + return ( + +
+
+
+ +
+
+

{guide.name}

+

{guide.tagline}

+
+
+

+ {guide.whatItIs} +

+ +
+
+

+ Key Concepts to Learn +

+
    + {guide.keyConcepts.map((concept, idx) => ( +
  • + • + {concept} +
  • + ))} +
+
+ +
+

+ Real-World Use Cases +

+
+ {guide.useCases.map((useCase, idx) => ( + + {useCase} + + ))} +
+ +

+ Official Documentation & Courses +

+
+ {guide.links.map((link, idx) => ( + + {link.label} + + + ))} +
+
+
+
+
+ ); + })() + ) : selectedCategory !== null ? ( + /* ── Tools inside selected Category ── */ + (() => { + const cat = categories[selectedCategory]; + const IconComp = cat.icon; + return ( + +
+
+ +
+
+

{cat.title}

+

+ {cat.tools.length} software tools & resources available +

+
+
+ +
+ {cat.tools.map((tool, idx) => ( + { + if (selectedToolkit === 'cs' && selectedCategory === 0) { + setSelectedLanguage(idx); + } else { + setSelectedTool({ ...tool, category: cat.title, bg: cat.bg, color: cat.color }); + } + }} + className="p-6 bg-white hover:bg-[#FFF7ED] rounded-2xl border border-[#E5E7EB] hover:border-[#FED7AA] cursor-pointer group transition-all flex flex-col justify-between" + > +
+
+

+ {tool.name} +

+ +
+

+ {tool.desc} +

+
+ + {selectedToolkit === 'cs' && selectedCategory === 0 ? 'View Beginner Guide & Concepts' : 'Explore Tool & Resources'} + + +
+ ))} +
+
+ ); + })() + ) : ( + /* ── Category Cards Grid ── */ +
+ {categories.map((cat, idx) => { + const IconComp = cat.icon; + return ( + setSelectedCategory(idx)} + className="p-7 bg-white hover:bg-[#FFF7ED] rounded-[22px] border border-[#E5E7EB] hover:border-[#FED7AA] cursor-pointer group transition-all shadow-xs flex flex-col justify-between" + > +
+
+ +
+

+ {cat.title} +

+

+ {cat.tools.length} curated tools and guides available. +

+
+
+ Browse Tools + +
+
+ ); + })} +
+ )} +
+ ); + })() + ) : ( +
+ {/* Toolkit Section Main */} +
+ + + {TOOLKIT_ITEMS.map((item) => { + const iconConfig = TOOLKIT_ICONS[item.title] || { icon: Code, bg: '#FFF7ED', color: '#F97316' }; + const IconComponent = iconConfig.icon; + return ( + + { + if (item.title === 'CS tools') { + setSelectedToolkit('cs'); + } else if (item.title === 'Business tools') { + setSelectedToolkit('business'); + } else if (item.title === 'Electrical and Electronic tools') { + setSelectedToolkit('electrical'); + } else if (item.title === 'Cybersecurity tools') { + setSelectedToolkit('cybersecurity'); + } else if (item.title === 'AI tools') { + setSelectedToolkit('ai'); + } else if (item.title === 'Biotech tools') { + setSelectedToolkit('biotech'); + } else if (item.url && item.url !== '#') { + window.open(item.url, '_blank'); + } + }} + whileHover={{ y: -4, boxShadow: '0 12px 30px -10px rgba(249,115,22,0.15)' }} + className="flex items-start gap-5 p-7 bg-white hover:bg-[#FFF7ED] rounded-[22px] border border-[#E5E7EB] hover:border-[#FED7AA] cursor-pointer group w-full transition-all shadow-xs hover:shadow-md" + > +
+ +
+
+
+ {item.title} +
+
+ {item.description} +
+
+ +
+
+ ); + })} +
+
+ )} +
+ + {/* Tool Modal */} + {selectedTool && ( +
+ +
+
+ +
+
+

{selectedTool.name}

+ {selectedTool.category} +
+
+

+ {selectedTool.desc} +

+
+ + {selectedTool.url && selectedTool.url !== '#' && ( + + Visit Official Website + + )} +
+
+
+ )} +
+ ); +}