diff --git a/package.json b/package.json
index dbe84a7..bedd93f 100644
--- a/package.json
+++ b/package.json
@@ -13,7 +13,9 @@
"@tailwindcss/vite": "^4.1.18",
"react": "^19.2.0",
"react-dom": "^19.2.0",
- "tailwindcss": "^4.1.18"
+ "react-router-dom": "^7.12.0",
+ "tailwindcss": "^4.1.18",
+ "zustand": "^5.0.9"
},
"devDependencies": {
"@eslint/js": "^9.39.1",
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index d95c070..83d5380 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -17,9 +17,15 @@ importers:
react-dom:
specifier: ^19.2.0
version: 19.2.3(react@19.2.3)
+ react-router-dom:
+ specifier: ^7.12.0
+ version: 7.12.0(react-dom@19.2.3(react@19.2.3))(react@19.2.3)
tailwindcss:
specifier: ^4.1.18
version: 4.1.18
+ zustand:
+ specifier: ^5.0.9
+ version: 5.0.9(@types/react@19.2.7)(react@19.2.3)
devDependencies:
'@eslint/js':
specifier: ^9.39.1
@@ -743,6 +749,10 @@ packages:
convert-source-map@2.0.0:
resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==}
+ cookie@1.1.1:
+ resolution: {integrity: sha512-ei8Aos7ja0weRpFzJnEA9UHJ/7XQmqglbRwnf2ATjcB9Wq874VKH9kfjjirM6UhU2/E5fFYadylyhFldcqSidQ==}
+ engines: {node: '>=18'}
+
cross-spawn@7.0.6:
resolution: {integrity: sha512-uV2QOWP2nWzsy2aMp8aRibhi9dlzF5Hgh5SHaB9OiTGEyDTiJJyx0uy51QXdyWbtAHNua4XJzUKca3OzKUd3vA==}
engines: {node: '>= 8'}
@@ -1126,6 +1136,23 @@ packages:
resolution: {integrity: sha512-QgT5//D3jfjJb6Gsjxv0Slpj23ip+HtOpnNgnb2S5zU3CB26G/IDPGoy4RJB42wzFE46DRsstbW6tKHoKbhAxw==}
engines: {node: '>=0.10.0'}
+ react-router-dom@7.12.0:
+ resolution: {integrity: sha512-pfO9fiBcpEfX4Tx+iTYKDtPbrSLLCbwJ5EqP+SPYQu1VYCXdy79GSj0wttR0U4cikVdlImZuEZ/9ZNCgoaxwBA==}
+ engines: {node: '>=20.0.0'}
+ peerDependencies:
+ react: '>=18'
+ react-dom: '>=18'
+
+ react-router@7.12.0:
+ resolution: {integrity: sha512-kTPDYPFzDVGIIGNLS5VJykK0HfHLY5MF3b+xj0/tTyNYL1gF1qs7u67Z9jEhQk2sQ98SUaHxlG31g1JtF7IfVw==}
+ engines: {node: '>=20.0.0'}
+ peerDependencies:
+ react: '>=18'
+ react-dom: '>=18'
+ peerDependenciesMeta:
+ react-dom:
+ optional: true
+
react@19.2.3:
resolution: {integrity: sha512-Ku/hhYbVjOQnXDZFv2+RibmLFGwFdeeKHFcOTlrt7xplBnya5OGn/hIRDsqDiSUcfORsDC7MPxwork8jBwsIWA==}
engines: {node: '>=0.10.0'}
@@ -1151,6 +1178,9 @@ packages:
engines: {node: '>=10'}
hasBin: true
+ set-cookie-parser@2.7.2:
+ resolution: {integrity: sha512-oeM1lpU/UvhTxw+g3cIfxXHyJRc/uidd3yK1P242gzHds0udQBYzs3y8j4gCCW+ZJ7ad0yctld8RYO+bdurlvw==}
+
shebang-command@2.0.0:
resolution: {integrity: sha512-kHxr2zZpYtdmrN1qDjrrX/Z1rR1kG8Dx+gkpK1G4eXmvXswmcE1hTWBWYUzlraYw1/yZp6YuDY77YtvbN0dmDA==}
engines: {node: '>=8'}
@@ -1281,6 +1311,24 @@ packages:
zod@4.3.5:
resolution: {integrity: sha512-k7Nwx6vuWx1IJ9Bjuf4Zt1PEllcwe7cls3VNzm4CQ1/hgtFUK2bRNG3rvnpPUhFjmqJKAKtjV576KnUkHocg/g==}
+ zustand@5.0.9:
+ resolution: {integrity: sha512-ALBtUj0AfjJt3uNRQoL1tL2tMvj6Gp/6e39dnfT6uzpelGru8v1tPOGBzayOWbPJvujM8JojDk3E1LxeFisBNg==}
+ engines: {node: '>=12.20.0'}
+ peerDependencies:
+ '@types/react': '>=18.0.0'
+ immer: '>=9.0.6'
+ react: '>=18.0.0'
+ use-sync-external-store: '>=1.2.0'
+ peerDependenciesMeta:
+ '@types/react':
+ optional: true
+ immer:
+ optional: true
+ react:
+ optional: true
+ use-sync-external-store:
+ optional: true
+
snapshots:
'@babel/code-frame@7.27.1':
@@ -1893,6 +1941,8 @@ snapshots:
convert-source-map@2.0.0: {}
+ cookie@1.1.1: {}
+
cross-spawn@7.0.6:
dependencies:
path-key: 3.1.1
@@ -2252,6 +2302,20 @@ snapshots:
react-refresh@0.18.0: {}
+ react-router-dom@7.12.0(react-dom@19.2.3(react@19.2.3))(react@19.2.3):
+ dependencies:
+ react: 19.2.3
+ react-dom: 19.2.3(react@19.2.3)
+ react-router: 7.12.0(react-dom@19.2.3(react@19.2.3))(react@19.2.3)
+
+ react-router@7.12.0(react-dom@19.2.3(react@19.2.3))(react@19.2.3):
+ dependencies:
+ cookie: 1.1.1
+ react: 19.2.3
+ set-cookie-parser: 2.7.2
+ optionalDependencies:
+ react-dom: 19.2.3(react@19.2.3)
+
react@19.2.3: {}
resolve-from@4.0.0: {}
@@ -2293,6 +2357,8 @@ snapshots:
semver@7.7.3: {}
+ set-cookie-parser@2.7.2: {}
+
shebang-command@2.0.0:
dependencies:
shebang-regex: 3.0.0
@@ -2378,3 +2444,8 @@ snapshots:
zod: 4.3.5
zod@4.3.5: {}
+
+ zustand@5.0.9(@types/react@19.2.7)(react@19.2.3):
+ optionalDependencies:
+ '@types/react': 19.2.7
+ react: 19.2.3
diff --git a/src/App.css b/src/App.css
deleted file mode 100644
index e69de29..0000000
diff --git a/src/App.tsx b/src/App.tsx
index 36533fa..f4f8af2 100644
--- a/src/App.tsx
+++ b/src/App.tsx
@@ -1,10 +1,27 @@
-import "./App.css";
+import { BrowserRouter, Routes, Route, Navigate } from "react-router-dom";
+import { Login } from "./pages/login";
+import { StudentDashboard } from "./pages/StudentDashboard";
+import { ProtectedRoute } from "./components/ProtectedRoute";
function App() {
return (
- <>
-
Edbridge Scholars
- >
+
+
+ } />
+
+ {/* Protected Routes */}
+ }>
+ } />
+ {/* Add more subroutes here as needed */}
+
+
+ {/* Redirect root to student */}
+ } />
+
+ {/* Catch all - redirect to student */}
+ } />
+
+
);
}
diff --git a/src/assets/auth.css b/src/assets/auth.css
new file mode 100644
index 0000000..2c3d7c8
--- /dev/null
+++ b/src/assets/auth.css
@@ -0,0 +1,172 @@
+/*
+* Prefixed by https://autoprefixer.github.io
+* PostCSS: v8.4.14,
+* Autoprefixer: v10.4.7
+* Browsers: last 4 version
+*/
+
+/*
+* Prefixed by https://autoprefixer.github.io
+* PostCSS: v8.4.14,
+* Autoprefixer: v10.4.7
+* Browsers: last 4 version
+*/
+
+/* Auth Pages Styling */
+.login-container {
+ min-height: 100vh;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ background-color: var(--secondary-bg);
+ background-image: -o-linear-gradient(315deg, #f5f5f5 0%, #ffffff 100%);
+ background-image: linear-gradient(135deg, #f5f5f5 0%, #ffffff 100%);
+ padding: 1rem;
+}
+
+.auth-container {
+ max-width: 420px;
+ width: 100%;
+ padding: 2.5rem;
+ border-radius: 12px;
+ -webkit-box-shadow: 0 8px 24px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 8px 24px rgba(0, 0, 0, 0.08);
+ background-color: var(--tertiary-bg);
+ border: 1px solid var(--secondary-border);
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.auth-container:hover {
+ -webkit-box-shadow: 0 12px 32px rgba(0, 0, 0, 0.12);
+ box-shadow: 0 12px 32px rgba(0, 0, 0, 0.12);
+ -webkit-transform: translateY(-5px);
+ -ms-transform: translateY(-5px);
+ transform: translateY(-5px);
+}
+
+.auth-title {
+ text-align: center;
+ margin-bottom: 1.5rem;
+ color: var(--intensive-text);
+ font-weight: 700;
+ font-size: 1.75rem;
+}
+
+.auth-footer {
+ text-align: center;
+ margin-top: 1.5rem;
+ font-size: 0.9rem;
+ color: var(--neutral);
+}
+
+.auth-footer a {
+ color: var(--primary-text);
+ font-weight: 500;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.auth-footer a:hover {
+ text-decoration: underline;
+}
+
+/* Form Styling */
+.auth-container .field {
+ margin-bottom: 1.25rem;
+}
+
+.auth-container .label {
+ color: var(--intensive-text) !important;
+ font-weight: 600;
+ font-size: 0.9rem;
+ margin-bottom: 0.5rem;
+}
+
+.auth-container .input {
+ color: var(--intensive-text) !important;
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ padding: 0.75rem 1rem;
+ height: auto;
+ font-size: 1rem;
+ -webkit-box-shadow: none;
+ box-shadow: none;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.auth-container .input:focus {
+ border-color: var(--primary-bg);
+ -webkit-box-shadow: 0 0 0 2px rgba(110, 68, 255, 0.1);
+ box-shadow: 0 0 0 2px rgba(110, 68, 255, 0.1);
+}
+
+.auth-container .input.is-danger {
+ border-color: var(--error-bg);
+}
+
+.auth-container .button {
+ height: auto;
+ padding: 0.75rem 1.5rem;
+ font-weight: 600;
+ font-size: 1rem;
+ border-radius: 8px;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.auth-container .button.is-primary {
+ background-color: var(--primary-bg);
+ border: none;
+}
+
+.auth-container .button.is-primary:hover {
+ background-color: var(--primary-dark);
+ -webkit-box-shadow: 0 4px 12px rgba(110, 68, 255, 0.3);
+ box-shadow: 0 4px 12px rgba(110, 68, 255, 0.3);
+ -webkit-transform: translateY(-2px);
+ -ms-transform: translateY(-2px);
+ transform: translateY(-2px);
+}
+
+.auth-container .checkbox {
+ font-size: 0.9rem;
+ color: var(--neutral-dark);
+}
+
+.auth-container .help.is-danger {
+ font-size: 0.8rem;
+ margin-top: 0.25rem;
+}
+
+.auth-container .notification {
+ border-radius: 8px;
+ padding: 1rem;
+ margin-bottom: 1.5rem;
+}
+
+.auth-container .notification .delete {
+ position: absolute;
+ right: 0.75rem;
+ top: 0.75rem;
+}
+
+/* Responsive Adjustments */
+@media screen and (max-width: 768px) {
+ .auth-container {
+ padding: 2rem;
+ max-width: 100%;
+ margin: 0 1rem;
+ }
+}
diff --git a/src/assets/custom.css b/src/assets/custom.css
new file mode 100644
index 0000000..7c6687a
--- /dev/null
+++ b/src/assets/custom.css
@@ -0,0 +1,2087 @@
+/*
+* Prefixed by https://autoprefixer.github.io
+* PostCSS: v8.4.14,
+* Autoprefixer: v10.4.7
+* Browsers: last 4 version
+*/
+
+/* Custom Bulma Variables */
+:root {
+ /* Primary Colors */
+ --primary: #6e44ff;
+ --primary-light: #9f84ff;
+ --primary-dark: #1f0954;
+
+ /* Neutral Colors */
+ --black: #000000;
+ --white: #ffffff;
+ --neutral-lightest: #f7f7f7;
+ --neutral-lighter: #ececec;
+ --neutral-light: #aaaaaa;
+ --neutral: #666666;
+ --neutral-dark: #444444;
+ --neutral-darker: #222222;
+ --neutral-darkest: #111111;
+
+ /* Color Neutral */
+ --neutral-lightest: #eeeeee;
+ --neutral-lighter: #cccccc;
+ --neutral-light: #aaaaaa;
+ --neutral: #666666;
+ --neutral-dark: #444444;
+ --neutral-darker: #222222;
+ --neutral-darkest: #111111;
+
+ /* Success Colors */
+ --success-green: #00c7a4;
+ --success-green-light: #7cfff3;
+
+ /* Error Colors */
+ --error-red: #ff2c73;
+ --error-red-light: #fff2f2;
+
+ /* Semantic Colors */
+ --primary-bg: #6e44ff;
+ --secondary-bg: #eeeeee;
+ --tertiary-bg: #ffffff;
+ --intensive-bg: #000000;
+ --success-bg: #00c7a4;
+ --error-bg: #ff2c73;
+
+ /* Border Colors */
+ --primary-border: #000000;
+ --secondary-border: #cccccc;
+ --tertiary-border: #1f0954;
+ --intensive-border: #000000;
+ --success-border: #00c7a4;
+ --error-border: #ff2c73;
+
+ /* Text Colors */
+ --primary-text: #6e44ff;
+ --secondary-text: #9f84ff;
+ --intensive-text: #000000;
+ --success-text: #00c7a4;
+ --error-text: #ff2c73;
+ --link-text: #6e44ff;
+}
+
+/* Bulma Customization */
+body {
+ font-family: "Satoshi", sans-serif;
+ background-color: var(--tertiary-bg);
+ color: var(--intensive-text);
+}
+
+/* Navbar Styling */
+.navbar {
+ background-color: var(--tertiary-bg);
+ color: var(--intensive-text);
+ -webkit-box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
+ height: 4rem;
+ border-bottom: 1px solid var(--secondary-border);
+ position: sticky;
+ top: 0;
+ z-index: 30;
+}
+
+.navbar-item,
+.navbar-link {
+ color: var(--intensive-text);
+ font-weight: 500;
+}
+
+.navbar-item:hover,
+.navbar-link:hover {
+ background-color: var(--secondary-bg) !important;
+ color: var(--primary-text) !important;
+}
+
+.navbar-brand .navbar-item {
+ font-weight: 700;
+ font-size: 1.25rem;
+ color: var(--primary-text);
+}
+
+.navbar-item img {
+ max-height: 2.5rem;
+}
+
+.navbar-burger {
+ color: var(--intensive-text);
+}
+
+.navbar-menu.is-active {
+ background-color: var(--tertiary-bg);
+ -webkit-box-shadow: 0 4px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 4px 8px rgba(0, 0, 0, 0.05);
+}
+
+/* Button Styling */
+.button {
+ font-family: "Satoshi", sans-serif;
+ font-weight: 500;
+ border-radius: 4px;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.button.is-primary {
+ background-color: var(--primary-bg);
+ border: none;
+ color: white;
+}
+
+.button.is-primary:hover {
+ background-color: var(--primary-dark);
+ -webkit-box-shadow: 0 4px 8px rgba(110, 68, 255, 0.2);
+ box-shadow: 0 4px 8px rgba(110, 68, 255, 0.2);
+ color: white;
+}
+
+.button.is-success {
+ background-color: var(--success-bg);
+ color: white;
+}
+
+.button.is-success:hover {
+ background-color: var(--success-green-light);
+ -webkit-box-shadow: 0 4px 8px rgba(0, 199, 164, 0.2);
+ box-shadow: 0 4px 8px rgba(0, 199, 164, 0.2);
+ color: white;
+}
+
+.button.is-danger {
+ background-color: var(--error-bg);
+ color: white;
+}
+
+.button.is-danger:hover {
+ background-color: var(--error-red-light);
+ color: var(--error-red);
+ -webkit-box-shadow: 0 4px 8px rgba(255, 44, 115, 0.2);
+ box-shadow: 0 4px 8px rgba(255, 44, 115, 0.2);
+}
+
+.button.is-outlined {
+ border: 1px solid var(--primary-border);
+ color: var(--primary-text);
+ background: transparent;
+}
+
+.button.is-outlined:hover {
+ background-color: var(--secondary-bg);
+}
+
+.button.is-info {
+ background-color: #3e8ed0;
+ color: white;
+}
+
+.button.is-info:hover {
+ background-color: #3082c5;
+ color: white;
+}
+
+.button.is-warning {
+ background-color: #ffe08a;
+ color: rgba(0, 0, 0, 0.7);
+}
+
+.button.is-warning:hover {
+ background-color: #ffda6a;
+ color: rgba(0, 0, 0, 0.7);
+}
+
+/* Sidebar Styling */
+.sidebar {
+ background-color: var(--tertiary-bg);
+ height: calc(100vh - 4rem);
+ width: 260px;
+ position: fixed;
+ z-index: 20;
+ top: 4rem;
+ left: 0;
+ overflow-y: auto;
+ padding: 0;
+ border-right: 1px solid var(--secondary-border);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -webkit-box-shadow: 1px 0 5px rgba(0, 0, 0, 0.05);
+ box-shadow: 1px 0 5px rgba(0, 0, 0, 0.05);
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.sidebar-header {
+ padding: 1.5rem 1.5rem 0.5rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ border-bottom: 1px solid var(--secondary-border);
+ margin-bottom: 1rem;
+}
+
+.sidebar-header h3 {
+ font-size: 0.85rem;
+ text-transform: uppercase;
+ letter-spacing: 1.5px;
+ color: var(--neutral);
+ font-weight: 600;
+}
+
+.sidebar-menu {
+ list-style: none;
+ margin: 0;
+ padding: 0.75rem 0;
+ -webkit-box-flex: 1;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+}
+
+.sidebar-item {
+ margin: 0.25rem 0.75rem;
+}
+
+.sidebar-link {
+ padding: 0.75rem 1rem;
+ text-decoration: none;
+ font-size: 0.9rem;
+ color: var(--neutral-darker);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ border-radius: 6px;
+ font-weight: 500;
+ position: relative;
+ overflow: hidden;
+}
+
+.sidebar-link:hover {
+ background-color: var(--secondary-bg);
+ color: var(--primary-text);
+ -webkit-transform: translateX(2px);
+ -ms-transform: translateX(2px);
+ transform: translateX(2px);
+}
+
+.sidebar-link.is-active {
+ background-color: rgba(110, 68, 255, 0.1);
+ color: var(--primary-text);
+ font-weight: 600;
+ position: relative;
+}
+
+.sidebar-link.is-active::before {
+ content: "";
+ position: absolute;
+ left: 0;
+ top: 0;
+ height: 100%;
+ width: 4px;
+ background-color: var(--primary-bg);
+ border-radius: 0 2px 2px 0;
+}
+
+.sidebar-link i {
+ margin-right: 0.75rem;
+ font-size: 1rem;
+ width: 20px;
+ text-align: center;
+ color: var(--neutral);
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.sidebar-link:hover i,
+.sidebar-link.is-active i {
+ color: var(--primary-text);
+}
+
+.sidebar-section-title {
+ font-size: 0.7rem;
+ text-transform: uppercase;
+ letter-spacing: 1.5px;
+ color: var(--neutral);
+ font-weight: 600;
+ padding: 0.75rem 1.75rem 0.5rem;
+ margin-top: 0.5rem;
+}
+
+.sidebar-footer {
+ padding: 1rem;
+ border-top: 1px solid var(--secondary-border);
+ text-align: center;
+ font-size: 0.75rem;
+ color: var(--neutral);
+}
+
+.main-content {
+ margin-left: 260px;
+ padding: 2rem;
+ min-height: calc(100vh - 4rem);
+ background-color: var(--tertiary-bg);
+}
+
+/* Mobile Responsiveness */
+@media screen and (max-width: 768px) {
+ .sidebar {
+ width: 100%;
+ height: auto;
+ position: relative;
+ top: 0;
+ display: none;
+ }
+
+ .sidebar.is-active {
+ display: block;
+ }
+
+ .main-content {
+ margin-left: 0;
+ }
+}
+
+/* Card Styling */
+.card {
+ border-radius: 8px;
+ -webkit-box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ -webkit-transition: -webkit-box-shadow 0.3s ease, -webkit-transform 0.2s ease;
+ transition: -webkit-box-shadow 0.3s ease, -webkit-transform 0.2s ease;
+ -o-transition: box-shadow 0.3s ease, transform 0.2s ease;
+ transition: box-shadow 0.3s ease, transform 0.2s ease;
+ transition: box-shadow 0.3s ease, transform 0.2s ease,
+ -webkit-box-shadow 0.3s ease, -webkit-transform 0.2s ease;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+ background-color: var(--tertiary-bg);
+ margin-bottom: 1.5rem;
+}
+
+.card:hover {
+ -webkit-box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ -webkit-transform: translateY(-2px);
+ -ms-transform: translateY(-2px);
+ transform: translateY(-2px);
+}
+
+/* Student Home Page Styling */
+.continue-learning-card {
+ border-radius: 8px;
+ overflow: hidden;
+ -webkit-box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ border: 1px solid var(--secondary-border);
+ height: 100%;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+}
+
+.continue-learning-card .card-content {
+ padding: 0;
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+}
+
+.learning-card-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 0.5rem 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.learning-card-header .tag {
+ margin-right: 0.5rem;
+ background-color: #e8f4ff;
+ color: #0086ff;
+ border-radius: 4px;
+ font-weight: 500;
+ font-size: 0.7rem;
+}
+
+.learning-card-body {
+ padding: 0.75rem 1rem 1rem;
+}
+
+.learning-card-title {
+ font-size: 1rem;
+ font-weight: 600;
+ margin-bottom: 0.75rem;
+ color: var(--intensive-text);
+ line-height: 1.3;
+ height: 2.6rem;
+ overflow: hidden;
+ display: -webkit-box;
+ -webkit-line-clamp: 2;
+ -webkit-box-orient: vertical;
+}
+
+.learning-card-progress {
+ margin-bottom: 0.75rem;
+}
+
+.learning-card-progress-text {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ margin-bottom: 0.25rem;
+ font-size: 0.75rem;
+ color: var(--neutral);
+}
+
+.learning-card-progress .progress {
+ height: 0.4rem;
+ border-radius: 4px;
+}
+
+.learning-card-progress .progress::-webkit-progress-bar {
+ background-color: #f0f0f0;
+}
+
+.learning-card-progress .progress::-webkit-progress-value {
+ background-color: #00c48c;
+}
+
+.continue-button {
+ background-color: white;
+ color: var(--primary-bg);
+ border: 1px solid var(--primary-bg);
+ border-radius: 6px;
+ padding: 0.4rem 1rem;
+ font-weight: 500;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ font-size: 0.8rem;
+}
+
+.continue-button:hover {
+ background-color: var(--primary-bg);
+ color: white;
+}
+
+/* SAT Dates Section Styling */
+.sat-dates-container {
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+ margin-bottom: 1.5rem;
+}
+
+.sat-dates-header {
+ background-color: #f9f9f9;
+ padding: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.sat-dates-body {
+ padding: 0;
+}
+
+.sat-dates-table {
+ width: 100%;
+ border-collapse: collapse;
+}
+
+.sat-dates-table th {
+ background-color: #f9f9f9;
+ padding: 0.75rem 1rem;
+ font-weight: 600;
+ font-size: 0.9rem;
+ color: var(--neutral-dark);
+ text-align: left;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.sat-dates-table td {
+ padding: 0.75rem 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+ font-size: 0.9rem;
+}
+
+.sat-dates-table tr:last-child td {
+ border-bottom: none;
+}
+
+.sat-dates-footer {
+ background-color: #f9f9f9;
+ padding: 0.75rem 1rem;
+ border-top: 1px solid var(--secondary-border);
+ text-align: center;
+}
+
+.sat-dates-footer a {
+ color: var(--primary-bg);
+ text-decoration: none;
+ font-weight: 500;
+ font-size: 0.9rem;
+}
+
+.sat-dates-footer a:hover {
+ text-decoration: underline;
+}
+
+.register-button {
+ background-color: var(--primary-bg);
+ color: white;
+ border: none;
+ border-radius: 4px;
+ padding: 0.4rem 0.75rem;
+ font-size: 0.8rem;
+ font-weight: 500;
+ cursor: pointer;
+ -webkit-transition: background-color 0.2s ease;
+ -o-transition: background-color 0.2s ease;
+ transition: background-color 0.2s ease;
+}
+
+.register-button:hover {
+ background-color: #5a38d9;
+}
+
+.sat-tips-container {
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+ height: 100%;
+}
+
+.sat-tips-header {
+ background-color: #f9f9f9;
+ padding: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.sat-tips-body {
+ padding: 1rem;
+}
+
+.sat-tips-list {
+ list-style-type: none;
+ padding: 0;
+ margin: 0;
+}
+
+.sat-tips-list li {
+ padding: 0.5rem 0;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: start;
+ -ms-flex-align: start;
+ align-items: flex-start;
+}
+
+.sat-tips-list li:before {
+ content: "•";
+ color: var(--primary-bg);
+ font-weight: bold;
+ display: inline-block;
+ width: 1em;
+ margin-right: 0.5em;
+}
+
+/* Settings Page Styling */
+.settings-container {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ gap: 1.5rem;
+}
+
+.settings-sidebar {
+ -webkit-box-flex: 0;
+ -ms-flex: 0 0 250px;
+ flex: 0 0 250px;
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+}
+
+.settings-sidebar-header {
+ background-color: #f9f9f9;
+ padding: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.settings-sidebar-body {
+ padding: 1rem 0;
+}
+
+.menu-list a {
+ border-radius: 0;
+ padding: 0.75rem 1.25rem;
+ margin-bottom: 0;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ border-left: 3px solid transparent;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.menu-list a:hover {
+ background-color: var(--secondary-bg);
+ color: var(--primary-bg);
+ border-left-color: var(--secondary-border);
+}
+
+.menu-list a.is-active {
+ background-color: #f0f0ff;
+ color: var(--primary-bg);
+ font-weight: 500;
+ border-left-color: var(--primary-bg);
+}
+
+.menu-list a .icon {
+ margin-right: 0.75rem;
+ font-size: 0.9rem;
+ width: 20px;
+ text-align: center;
+}
+
+.menu-label {
+ color: var(--neutral-dark);
+ font-weight: 600;
+ text-transform: uppercase;
+ letter-spacing: 0.5px;
+ font-size: 0.75rem;
+ margin-top: 1.5rem;
+ margin-bottom: 0.75rem;
+ padding: 0 1.25rem;
+}
+
+.settings-content {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+}
+
+.settings-panel {
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+ margin-bottom: 1.5rem;
+}
+
+.settings-panel-header {
+ background-color: #f9f9f9;
+ padding: 1rem 1.5rem;
+ border-bottom: 1px solid var(--secondary-border);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.settings-panel-header .icon {
+ margin-right: 0.75rem;
+ color: var(--primary-bg);
+}
+
+.settings-panel-body {
+ padding: 1.5rem;
+}
+
+.settings-panel-footer {
+ background-color: #f9f9f9;
+ padding: 1rem 1.5rem;
+ border-top: 1px solid var(--secondary-border);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: end;
+ -ms-flex-pack: end;
+ justify-content: flex-end;
+}
+
+/* Progress Page Styling */
+.metric-card {
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ padding: 1.25rem;
+ position: relative;
+ overflow: hidden;
+ height: 100%;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -webkit-box-align: start;
+ -ms-flex-align: start;
+ align-items: flex-start;
+ -webkit-box-pack: start;
+ -ms-flex-pack: start;
+ justify-content: flex-start;
+ background-color: white;
+}
+
+.metric-value {
+ font-size: 2.5rem;
+ font-weight: 700;
+ color: var(--primary-bg);
+ margin-bottom: 0.5rem;
+ line-height: 1;
+}
+
+.metric-label {
+ font-size: 0.75rem;
+ color: var(--neutral);
+ font-weight: 500;
+ text-transform: uppercase;
+ letter-spacing: 0.5px;
+}
+
+.metric-icon {
+ position: absolute;
+ bottom: 1rem;
+ right: 1rem;
+ color: rgba(110, 68, 255, 0.1);
+ font-size: 2rem;
+ opacity: 0.5;
+}
+
+.progress-panel {
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ overflow: hidden;
+ margin-bottom: 1.5rem;
+}
+
+.progress-panel-header {
+ background-color: #f9f9f9;
+ padding: 1rem 1.5rem;
+ border-bottom: 1px solid var(--secondary-border);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.progress-panel-header .icon {
+ margin-right: 0.75rem;
+ color: var(--primary-bg);
+}
+
+.progress-panel-body {
+ padding: 1.5rem;
+}
+
+.subject-performance {
+ margin-bottom: 1.5rem;
+}
+
+.subject-label {
+ font-weight: 500;
+ color: var(--neutral-dark);
+}
+
+.subject-score {
+ font-weight: 600;
+ color: var(--primary-bg);
+}
+
+.progress-table {
+ width: 100%;
+ border-collapse: collapse;
+}
+
+.progress-table th {
+ background-color: #f9f9f9;
+ padding: 0.75rem 1rem;
+ font-weight: 600;
+ font-size: 0.9rem;
+ color: var(--neutral-dark);
+ text-align: left;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.progress-table td {
+ padding: 0.75rem 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+ font-size: 0.9rem;
+}
+
+.progress-table tr:last-child td {
+ border-bottom: none;
+}
+
+.practice-sheet-card {
+ position: relative;
+ overflow: hidden;
+}
+
+.practice-sheet-card-icon {
+ position: absolute;
+ top: 1rem;
+ right: 1rem;
+ opacity: 0.8;
+}
+
+.option-item {
+ padding: 1rem;
+ border: 1px solid var(--secondary-border);
+ border-radius: 8px;
+ margin-bottom: 1rem;
+ cursor: pointer;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.option-item:hover {
+ background-color: var(--secondary-bg);
+}
+
+.option-item.selected {
+ border-color: var(--primary-bg);
+ background-color: rgba(110, 68, 255, 0.05);
+}
+
+.option-marker {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ width: 30px;
+ height: 30px;
+ border-radius: 50%;
+ background-color: var(--secondary-bg);
+ color: var(--neutral-dark);
+ font-weight: 600;
+}
+
+.option-item.selected .option-marker {
+ background-color: var(--primary-bg);
+ color: white;
+}
+
+.score-display {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin: 1rem 0;
+}
+
+.score-circle {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ width: 180px;
+ height: 180px;
+ border-radius: 50%;
+ background-color: var(--primary-bg);
+ color: white;
+ -webkit-box-shadow: 0 4px 12px rgba(110, 68, 255, 0.2);
+ box-shadow: 0 4px 12px rgba(110, 68, 255, 0.2);
+}
+
+.score-value {
+ font-size: 3rem;
+ font-weight: 700;
+ line-height: 1;
+ margin-bottom: 0.5rem;
+}
+
+.score-label {
+ font-size: 0.9rem;
+ font-weight: 500;
+ text-align: center;
+ max-width: 80%;
+}
+
+.section-score {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 1.5rem;
+ background-color: #f9f9f9;
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ height: 100%;
+}
+
+.section-score-value {
+ font-size: 2.5rem;
+ font-weight: 700;
+ color: var(--primary-bg);
+ margin-bottom: 0.5rem;
+ line-height: 1;
+}
+
+.section-score-label {
+ font-size: 0.9rem;
+ font-weight: 500;
+ color: var(--neutral);
+}
+
+.module-score-item {
+ border: 1px solid var(--secondary-border);
+ border-radius: 8px;
+ padding: 1rem;
+ background-color: white;
+}
+
+.answer-sheet {
+ border-radius: 6px;
+ font-size: 0.9rem;
+ max-height: 300px;
+ overflow-y: auto;
+}
+
+.answer-item {
+ padding-bottom: 0.5rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.answer-item:last-child {
+ border-bottom: none;
+ padding-bottom: 0;
+}
+
+.subject-performance {
+ margin-bottom: 1.5rem;
+}
+
+.subject-label {
+ font-weight: 600;
+ color: var(--neutral-dark);
+}
+
+.subject-score {
+ font-weight: 700;
+ color: var(--primary-bg);
+}
+
+.card-header {
+ border-bottom: 1px solid var(--secondary-border);
+ background-color: var(--tertiary-bg);
+ -webkit-box-shadow: none;
+ box-shadow: none;
+}
+
+.card-header-title {
+ font-weight: 600;
+ font-size: 1.1rem;
+ color: var(--primary-text);
+}
+
+.card-content {
+ padding: 1.5rem;
+}
+
+.card-footer {
+ border-top: 1px solid var(--secondary-border);
+ background-color: var(--tertiary-bg);
+}
+
+/* Table Styling */
+.table {
+ width: 100%;
+ border-collapse: separate;
+ border-spacing: 0;
+ border-radius: 8px;
+ overflow: hidden;
+ -webkit-box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ margin-bottom: 2rem;
+}
+
+.table thead th {
+ background-color: var(--secondary-bg);
+ font-weight: 600;
+ color: var(--intensive-text);
+ text-transform: uppercase;
+ font-size: 0.8rem;
+ letter-spacing: 0.5px;
+ padding: 1rem;
+}
+
+.table td {
+ padding: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+ vertical-align: middle;
+}
+
+.table tr:last-child td {
+ border-bottom: none;
+}
+
+.table tr:hover {
+ background-color: var(--secondary-bg);
+}
+
+/* Form Styling */
+.field-label {
+ font-weight: 500;
+ color: var(--intensive-text);
+ font-size: 0.9rem;
+}
+
+.input,
+.textarea,
+.select select {
+ border-radius: 6px;
+ border: 1px solid var(--secondary-border);
+ -webkit-box-shadow: none;
+ box-shadow: none;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ background-color: var(--tertiary-bg);
+}
+
+.input:focus,
+.textarea:focus,
+.select select:focus {
+ border-color: var(--primary-bg);
+ -webkit-box-shadow: 0 0 0 2px rgba(110, 68, 255, 0.1);
+ box-shadow: 0 0 0 2px rgba(110, 68, 255, 0.1);
+}
+
+.input:hover,
+.textarea:hover,
+.select select:hover {
+ border-color: var(--primary-light);
+}
+
+/* Dashboard Header */
+.dashboard-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin-bottom: 1.5rem;
+ padding-bottom: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.dashboard-header .title {
+ margin-bottom: 0;
+ font-weight: 700;
+ color: var(--intensive-text);
+}
+
+/* Dashboard Metrics */
+.metric-card {
+ text-align: center;
+ padding: 1.5rem;
+ position: relative;
+ overflow: hidden;
+ border-radius: 8px;
+ border: 1px solid var(--secondary-border);
+ background-color: var(--tertiary-bg);
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+ height: 100%;
+}
+
+.metric-card:hover {
+ -webkit-transform: translateY(-5px);
+ -ms-transform: translateY(-5px);
+ transform: translateY(-5px);
+ -webkit-box-shadow: 0 8px 16px rgba(0, 0, 0, 0.1);
+ box-shadow: 0 8px 16px rgba(0, 0, 0, 0.1);
+}
+
+.metric-value {
+ font-size: 2.5rem;
+ font-weight: 700;
+ color: var(--primary-text);
+ line-height: 1.2;
+ margin-bottom: 0.5rem;
+}
+
+.metric-label {
+ font-size: 0.9rem;
+ color: var(--neutral);
+ text-transform: uppercase;
+ letter-spacing: 0.5px;
+ font-weight: 500;
+}
+
+.metric-icon {
+ position: absolute;
+ bottom: 1rem;
+ right: 1rem;
+ font-size: 3rem;
+ opacity: 0.1;
+ color: var(--primary-text);
+}
+
+/* Graph Container */
+.graph-container {
+ background-color: var(--tertiary-bg);
+ border-radius: 8px;
+ padding: 1.5rem;
+ -webkit-box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ border: 1px solid var(--secondary-border);
+ margin-bottom: 2rem;
+}
+
+.graph-title {
+ font-weight: 600;
+ font-size: 1.1rem;
+ margin-bottom: 1.5rem;
+ color: var(--intensive-text);
+}
+
+/* Enrollment Chart */
+.enrollment-chart-container {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ width: 100%;
+}
+
+.enrollment-chart {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ height: 100%;
+ width: 100%;
+}
+
+.chart-bars {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: end;
+ -ms-flex-align: end;
+ align-items: flex-end;
+ height: 85%;
+ width: 100%;
+ padding-bottom: 10px;
+}
+
+.chart-bar {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ margin: 0 4px;
+ border-radius: 4px 4px 0 0;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.chart-bar:hover {
+ -webkit-transform: scaleY(1.05);
+ -ms-transform: scaleY(1.05);
+ transform: scaleY(1.05);
+ -webkit-box-shadow: 0 0 10px rgba(110, 68, 255, 0.3);
+ box-shadow: 0 0 10px rgba(110, 68, 255, 0.3);
+}
+
+.chart-labels {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ width: 100%;
+ padding: 0 4px;
+}
+
+.chart-label {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ text-align: center;
+ font-size: 0.75rem;
+ color: var(--neutral);
+ font-weight: 500;
+}
+
+/* Subject Performance */
+.subject-performance {
+ margin-bottom: 1.25rem;
+}
+
+.subject-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ margin-bottom: 0.5rem;
+}
+
+.subject-name {
+ font-weight: 500;
+ font-size: 0.9rem;
+}
+
+.subject-score {
+ font-weight: 600;
+ color: var(--primary-text);
+}
+
+/* Difficulty Distribution */
+.difficulty-distribution {
+ margin-bottom: 1.25rem;
+}
+
+.difficulty-label {
+ font-weight: 500;
+ color: var(--primary-text);
+ font-size: 0.9rem;
+}
+
+.difficulty-count {
+ font-weight: 600;
+ color: var(--primary-text);
+}
+
+/* Activity Statistics */
+.activity-summary {
+ margin-bottom: 1.25rem;
+}
+
+.stat-label {
+ font-weight: 500;
+ color: var(--neutral-dark);
+ font-size: 0.9rem;
+}
+
+.stat-value {
+ font-weight: 600;
+ color: var(--primary-text);
+}
+
+.activity-item {
+ padding: 0.75rem;
+ border-radius: 6px;
+ background-color: var(--neutral-lightest);
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.activity-item:hover {
+ background-color: var(--secondary-bg);
+ -webkit-transform: translateX(3px);
+ -ms-transform: translateX(3px);
+ transform: translateX(3px);
+}
+
+.student-name,
+.sheet-name {
+ font-size: 0.9rem;
+ line-height: 1.2;
+}
+
+.student-activity,
+.sheet-activity {
+ margin-top: 0.2rem;
+}
+
+.card-header-title .icon {
+ color: var(--primary-bg);
+ margin-right: 0.5rem;
+}
+
+.graph-title .icon {
+ margin-right: 0.5rem;
+ color: var(--primary-bg);
+}
+
+/* Practice Sheet Styling */
+.practice-sheet-card {
+ margin-bottom: 1.5rem;
+ position: relative;
+ overflow: hidden;
+}
+
+.practice-sheet-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin-bottom: 1.5rem;
+ padding-bottom: 1rem;
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.practice-sheet-detail {
+ position: relative;
+ padding: 2rem;
+ background-color: var(--tertiary-bg);
+ border-radius: 8px;
+ -webkit-box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05);
+ border: 1px solid var(--secondary-border);
+ margin-bottom: 2rem;
+}
+
+.practice-sheet-detail::before {
+ content: "Practice Sheet";
+ position: absolute;
+ top: -10px;
+ left: 20px;
+ background-color: var(--primary-bg);
+ color: white;
+ padding: 0.25rem 0.75rem;
+ border-radius: 20px;
+ font-size: 0.75rem;
+ font-weight: 600;
+ text-transform: uppercase;
+ letter-spacing: 0.5px;
+}
+
+.module-container {
+ margin-top: 2rem;
+ position: relative;
+}
+
+.module-list {
+ position: relative;
+}
+
+.module-list::before {
+ content: "";
+ position: absolute;
+ top: 0;
+ bottom: 0;
+ left: 20px;
+ width: 2px;
+ background-color: var(--secondary-border);
+ z-index: 0;
+}
+
+.module-card {
+ margin-bottom: 1.5rem;
+ border-left: 4px solid var(--primary-bg);
+ border-radius: 0 8px 8px 0;
+ position: relative;
+ z-index: 1;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.module-card:hover {
+ -webkit-box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+}
+
+.module-card::before {
+ content: "";
+ position: absolute;
+ top: 50%;
+ left: -12px;
+ width: 20px;
+ height: 20px;
+ background-color: var(--primary-bg);
+ border-radius: 50%;
+ -webkit-transform: translateY(-50%);
+ -ms-transform: translateY(-50%);
+ transform: translateY(-50%);
+ z-index: 2;
+}
+
+.module-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 1rem 1.5rem;
+ background-color: rgba(110, 68, 255, 0.05);
+ border-bottom: 1px solid var(--secondary-border);
+}
+
+.module-title {
+ font-weight: 600;
+ font-size: 1.1rem;
+ color: var(--primary-text);
+}
+
+.module-meta {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ gap: 1rem;
+ font-size: 0.85rem;
+ color: var(--neutral);
+}
+
+.module-meta-item {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.module-meta-item i {
+ margin-right: 0.5rem;
+ font-size: 0.9rem;
+}
+
+.module-content {
+ padding: 1.5rem;
+}
+
+.question-list {
+ position: relative;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ width: 100%;
+}
+
+.question-card {
+ margin-bottom: 1rem;
+ border-left: 3px solid var(--success-bg);
+ border-radius: 0 8px 8px 0;
+ background-color: var(--tertiary-bg);
+ position: relative;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+ width: 100%;
+}
+
+.question-card:hover {
+ -webkit-transform: translateX(5px);
+ -ms-transform: translateX(5px);
+ transform: translateX(5px);
+ -webkit-box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ border-left-color: var(--primary-bg);
+}
+
+.question-card.is-dragging {
+ -webkit-box-shadow: 0 8px 16px rgba(0, 0, 0, 0.15);
+ box-shadow: 0 8px 16px rgba(0, 0, 0, 0.15);
+ opacity: 0.9;
+ -webkit-transform: scale(1.02);
+ -ms-transform: scale(1.02);
+ transform: scale(1.02);
+ z-index: 10;
+}
+
+.question-drag-handle {
+ cursor: -webkit-grab;
+ cursor: grab;
+ color: var(--neutral);
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.question-drag-handle:hover {
+ color: var(--primary-bg);
+}
+
+.question-drag-handle:active {
+ cursor: -webkit-grabbing;
+ cursor: grabbing;
+}
+
+.question-index .tag {
+ font-weight: 600;
+ min-width: 40px;
+ text-align: center;
+}
+
+.question-card::before {
+ content: "";
+ position: absolute;
+ top: 50%;
+ left: -8px;
+ width: 12px;
+ height: 12px;
+ background-color: var(--success-bg);
+ border-radius: 50%;
+ -webkit-transform: translateY(-50%);
+ -ms-transform: translateY(-50%);
+ transform: translateY(-50%);
+}
+
+.question-header {
+ padding: 1rem 1.5rem;
+ border-bottom: 1px solid var(--secondary-border);
+ font-weight: 500;
+ -webkit-transition: background-color 0.2s ease;
+ -o-transition: background-color 0.2s ease;
+ transition: background-color 0.2s ease;
+ cursor: pointer;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.question-header:hover {
+ background-color: rgba(110, 68, 255, 0.05);
+}
+
+.question-header::after {
+ content: "";
+ position: absolute;
+ top: 50%;
+ right: 1rem;
+ -webkit-transform: translateY(-50%);
+ -ms-transform: translateY(-50%);
+ transform: translateY(-50%);
+ width: 0;
+ height: 0;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.question-content {
+ padding: 1rem 1.5rem;
+ -webkit-animation: fadeIn 0.3s ease;
+ animation: fadeIn 0.3s ease;
+}
+
+.question-options {
+ margin-top: 1rem;
+}
+
+.question-option {
+ padding: 0.75rem 1rem;
+ border: 1px solid var(--secondary-border);
+ border-radius: 6px;
+ margin-bottom: 0.5rem;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ cursor: pointer;
+}
+
+.question-option:hover {
+ background-color: var(--secondary-bg);
+}
+
+.question-option.is-correct {
+ border-color: var(--success-bg);
+ background-color: rgba(0, 199, 164, 0.05);
+}
+
+.question-explanation {
+ margin-top: 1rem;
+ padding: 1rem;
+ background-color: var(--secondary-bg);
+ border-radius: 6px;
+ font-size: 0.9rem;
+}
+
+/* Visual Connector Lines */
+.connector-line {
+ position: relative;
+}
+
+.connector-line::before {
+ content: "";
+ position: absolute;
+ top: 0;
+ bottom: 0;
+ left: 20px;
+ width: 2px;
+ background-color: var(--secondary-border);
+ z-index: 0;
+}
+
+.connector-dot {
+ position: absolute;
+ width: 12px;
+ height: 12px;
+ border-radius: 50%;
+ background-color: var(--primary-bg);
+ left: 15px;
+ top: 50%;
+ -webkit-transform: translateY(-50%);
+ -ms-transform: translateY(-50%);
+ transform: translateY(-50%);
+ z-index: 1;
+}
+
+/* Module Tabs Styling */
+.module-tabs-container {
+ position: relative;
+ margin-bottom: 2rem;
+}
+
+.module-tabs {
+ margin-bottom: 0;
+ overflow-x: auto;
+ white-space: nowrap;
+ position: relative;
+ z-index: 2;
+}
+
+.module-tabs ul {
+ border-bottom-color: var(--secondary-border);
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -ms-flex-wrap: nowrap;
+ flex-wrap: nowrap;
+}
+
+.module-tabs li {
+ -webkit-box-flex: 0;
+ -ms-flex: 0 0 auto;
+ flex: 0 0 auto;
+}
+
+.module-tabs li a {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 0.75rem 1.25rem;
+ border-radius: 4px 4px 0 0;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+ border-bottom: 2px solid transparent;
+ color: var(--neutral-darker);
+}
+
+.module-tabs li a:hover {
+ background-color: var(--secondary-bg);
+ color: var(--primary-text);
+}
+
+.module-tabs li.is-active a {
+ border-bottom-color: var(--primary-bg);
+ color: var(--primary-bg);
+ font-weight: 600;
+}
+
+.module-tabs li.tab-add-button a {
+ padding: 0.75rem;
+ color: var(--primary-bg);
+}
+
+.module-tab-content {
+ display: none;
+ padding: 1.5rem;
+ background-color: white;
+ border: 1px solid var(--secondary-border);
+ border-top: none;
+ border-radius: 0 0 8px 8px;
+ position: relative;
+ z-index: 1;
+}
+
+.module-tab-content.is-active {
+ display: block;
+ -webkit-animation: fadeIn 0.3s ease;
+ animation: fadeIn 0.3s ease;
+}
+
+@-webkit-keyframes fadeIn {
+ from {
+ opacity: 0;
+ }
+ to {
+ opacity: 1;
+ }
+}
+
+@keyframes fadeIn {
+ from {
+ opacity: 0;
+ }
+ to {
+ opacity: 1;
+ }
+}
+
+/* Module and Question Actions */
+.module-actions,
+.question-actions {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ gap: 0.5rem;
+ z-index: 10;
+}
+
+.module-actions .button,
+.question-actions .button {
+ padding: 0.5rem;
+ height: auto;
+}
+
+.question-text-container {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ overflow: hidden;
+ -o-text-overflow: ellipsis;
+ text-overflow: ellipsis;
+ white-space: nowrap;
+ max-width: 70%;
+ font-size: 0.95rem;
+ line-height: 1.5;
+}
+
+.question-text-full {
+ white-space: normal;
+ margin-top: 0.5rem;
+ margin-bottom: 1rem;
+ padding: 0.75rem 1rem;
+ background-color: var(--secondary-bg);
+ border-radius: 6px;
+ font-size: 1rem;
+ line-height: 1.6;
+ color: var(--intensive-text);
+ border-left: 3px solid var(--primary-bg);
+}
+
+/* Empty State */
+.empty-state {
+ text-align: center;
+ padding: 3rem 2rem;
+ background-color: var(--secondary-bg);
+ border-radius: 8px;
+ margin-bottom: 2rem;
+}
+
+.empty-state-icon {
+ font-size: 3rem;
+ color: var(--neutral-light);
+ margin-bottom: 1rem;
+}
+
+.empty-state-title {
+ font-size: 1.25rem;
+ font-weight: 600;
+ color: var(--neutral-dark);
+ margin-bottom: 0.5rem;
+}
+
+.empty-state-description {
+ color: var(--neutral);
+ margin-bottom: 1.5rem;
+ max-width: 400px;
+ margin-left: auto;
+ margin-right: auto;
+}
+
+/* User Management Styling */
+.user-avatar {
+ border-radius: 50%;
+ -o-object-fit: cover;
+ object-fit: cover;
+ border: 2px solid var(--secondary-border);
+}
+
+.user-card {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 1rem;
+ border-radius: 8px;
+ margin-bottom: 1rem;
+ background-color: var(--tertiary-bg);
+ border: 1px solid var(--secondary-border);
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.user-card:hover {
+ -webkit-box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
+ -webkit-transform: translateY(-2px);
+ -ms-transform: translateY(-2px);
+ transform: translateY(-2px);
+}
+
+.user-info {
+ margin-left: 1rem;
+}
+
+.user-name {
+ font-weight: 600;
+ font-size: 1.1rem;
+ margin-bottom: 0.25rem;
+}
+
+.user-email {
+ color: var(--neutral);
+ font-size: 0.9rem;
+}
+
+/* Badge Styling */
+.badge {
+ display: inline-block;
+ padding: 0.25rem 0.75rem;
+ border-radius: 20px;
+ font-size: 0.8rem;
+ font-weight: 500;
+ text-transform: uppercase;
+ letter-spacing: 0.5px;
+}
+
+.badge.is-primary {
+ background-color: var(--primary-bg);
+ color: white;
+}
+
+.badge.is-success {
+ background-color: var(--success-bg);
+ color: white;
+}
+
+.badge.is-error {
+ background-color: var(--error-bg);
+ color: white;
+}
+
+/* Timeline Styling */
+.timeline {
+ position: relative;
+ margin: 0 0 0 1rem;
+ padding-left: 1.5rem;
+}
+
+.timeline::before {
+ content: "";
+ position: absolute;
+ top: 0;
+ left: 0;
+ height: 100%;
+ width: 2px;
+ background-color: var(--secondary-border);
+}
+
+.timeline-item {
+ position: relative;
+ margin-bottom: 1.5rem;
+}
+
+.timeline-marker {
+ position: absolute;
+ left: -1.5rem;
+ width: 12px;
+ height: 12px;
+ border-radius: 50%;
+ background-color: var(--primary-bg);
+ top: 0.25rem;
+}
+
+.timeline-marker.is-primary {
+ background-color: var(--primary-bg);
+}
+
+.timeline-marker.is-success {
+ background-color: var(--success-bg);
+}
+
+.timeline-marker.is-warning {
+ background-color: #ffe08a;
+}
+
+.timeline-marker.is-danger {
+ background-color: var(--error-bg);
+}
+
+.timeline-content {
+ padding-bottom: 1rem;
+}
+
+.timeline-content .heading {
+ font-size: 0.8rem;
+ font-weight: 600;
+ color: var(--neutral);
+ margin-bottom: 0.25rem;
+}
+
+/* Info Item Styling */
+.info-item {
+ margin-bottom: 0.75rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.info-item strong {
+ min-width: 100px;
+ font-weight: 600;
+ color: var(--neutral-dark);
+}
+
+/* Auth Styling */
+.login-container {
+ min-height: 100vh;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ background-color: var(--secondary-bg);
+ background-image: -o-linear-gradient(
+ 315deg,
+ var(--secondary-bg) 0%,
+ var(--tertiary-bg) 100%
+ );
+ background-image: linear-gradient(
+ 135deg,
+ var(--secondary-bg) 0%,
+ var(--tertiary-bg) 100%
+ );
+}
+
+.auth-container {
+ max-width: 400px;
+ width: 100%;
+ padding: 2.5rem;
+ border-radius: 8px;
+ -webkit-box-shadow: 0 4px 16px rgba(0, 0, 0, 0.08);
+ box-shadow: 0 4px 16px rgba(0, 0, 0, 0.08);
+ background-color: var(--tertiary-bg);
+ border: 1px solid var(--secondary-border);
+}
+
+.auth-title {
+ text-align: center;
+ margin-bottom: 2rem;
+ color: var(--primary-text);
+ font-weight: 700;
+ font-size: 1.75rem;
+}
+
+.auth-footer {
+ text-align: center;
+ margin-top: 1.5rem;
+ font-size: 0.9rem;
+}
diff --git a/src/assets/ed_logo.png b/src/assets/ed_logo.png
new file mode 100644
index 0000000..b3c63f7
Binary files /dev/null and b/src/assets/ed_logo.png differ
diff --git a/src/assets/ed_logo1.png b/src/assets/ed_logo1.png
new file mode 100644
index 0000000..4c61e29
Binary files /dev/null and b/src/assets/ed_logo1.png differ
diff --git a/src/assets/fonts/Satoshi-Black.woff2 b/src/assets/fonts/Satoshi-Black.woff2
new file mode 100644
index 0000000..60586db
Binary files /dev/null and b/src/assets/fonts/Satoshi-Black.woff2 differ
diff --git a/src/assets/fonts/Satoshi-BlackItalic.woff2 b/src/assets/fonts/Satoshi-BlackItalic.woff2
new file mode 100644
index 0000000..b49b74c
Binary files /dev/null and b/src/assets/fonts/Satoshi-BlackItalic.woff2 differ
diff --git a/src/assets/fonts/Satoshi-Bold.woff2 b/src/assets/fonts/Satoshi-Bold.woff2
new file mode 100644
index 0000000..4c2a42a
Binary files /dev/null and b/src/assets/fonts/Satoshi-Bold.woff2 differ
diff --git a/src/assets/fonts/Satoshi-BoldItalic.woff2 b/src/assets/fonts/Satoshi-BoldItalic.woff2
new file mode 100644
index 0000000..dae39f9
Binary files /dev/null and b/src/assets/fonts/Satoshi-BoldItalic.woff2 differ
diff --git a/src/assets/fonts/Satoshi-Italic.woff2 b/src/assets/fonts/Satoshi-Italic.woff2
new file mode 100644
index 0000000..d4ce445
Binary files /dev/null and b/src/assets/fonts/Satoshi-Italic.woff2 differ
diff --git a/src/assets/fonts/Satoshi-Light.woff2 b/src/assets/fonts/Satoshi-Light.woff2
new file mode 100644
index 0000000..dee0f52
Binary files /dev/null and b/src/assets/fonts/Satoshi-Light.woff2 differ
diff --git a/src/assets/fonts/Satoshi-LightItalic.woff2 b/src/assets/fonts/Satoshi-LightItalic.woff2
new file mode 100644
index 0000000..fd5aa0e
Binary files /dev/null and b/src/assets/fonts/Satoshi-LightItalic.woff2 differ
diff --git a/src/assets/fonts/Satoshi-Medium.woff2 b/src/assets/fonts/Satoshi-Medium.woff2
new file mode 100644
index 0000000..46718c6
Binary files /dev/null and b/src/assets/fonts/Satoshi-Medium.woff2 differ
diff --git a/src/assets/fonts/Satoshi-MediumItalic.woff2 b/src/assets/fonts/Satoshi-MediumItalic.woff2
new file mode 100644
index 0000000..06f265b
Binary files /dev/null and b/src/assets/fonts/Satoshi-MediumItalic.woff2 differ
diff --git a/src/assets/fonts/Satoshi-Regular.woff2 b/src/assets/fonts/Satoshi-Regular.woff2
new file mode 100644
index 0000000..4adff66
Binary files /dev/null and b/src/assets/fonts/Satoshi-Regular.woff2 differ
diff --git a/src/assets/illustrations/Book lover-bro.svg b/src/assets/illustrations/Book lover-bro.svg
new file mode 100644
index 0000000..d9f2cea
--- /dev/null
+++ b/src/assets/illustrations/Book lover-bro.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/assets/illustrations/Circles-bro.svg b/src/assets/illustrations/Circles-bro.svg
new file mode 100644
index 0000000..3886c4d
--- /dev/null
+++ b/src/assets/illustrations/Circles-bro.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/assets/illustrations/learning_illustration.png b/src/assets/illustrations/learning_illustration.png
new file mode 100644
index 0000000..afdcd09
Binary files /dev/null and b/src/assets/illustrations/learning_illustration.png differ
diff --git a/src/assets/illustrations/student_learning.svg b/src/assets/illustrations/student_learning.svg
new file mode 100644
index 0000000..bd8f553
--- /dev/null
+++ b/src/assets/illustrations/student_learning.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/assets/illustrations/student_progress.svg b/src/assets/illustrations/student_progress.svg
new file mode 100644
index 0000000..f41cc34
--- /dev/null
+++ b/src/assets/illustrations/student_progress.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/src/assets/logo-dark.svg b/src/assets/logo-dark.svg
new file mode 100644
index 0000000..4de52bd
--- /dev/null
+++ b/src/assets/logo-dark.svg
@@ -0,0 +1,10 @@
+
diff --git a/src/assets/logo-purple.svg b/src/assets/logo-purple.svg
new file mode 100644
index 0000000..9c56b37
--- /dev/null
+++ b/src/assets/logo-purple.svg
@@ -0,0 +1,10 @@
+
diff --git a/src/assets/logo-white.svg b/src/assets/logo-white.svg
new file mode 100644
index 0000000..2b54340
--- /dev/null
+++ b/src/assets/logo-white.svg
@@ -0,0 +1,10 @@
+
diff --git a/src/assets/math-styles.css b/src/assets/math-styles.css
new file mode 100644
index 0000000..1260222
--- /dev/null
+++ b/src/assets/math-styles.css
@@ -0,0 +1,132 @@
+/*
+* Prefixed by https://autoprefixer.github.io
+* PostCSS: v8.4.14,
+* Autoprefixer: v10.4.7
+* Browsers: last 4 version
+*/
+
+/* Math Rendering Styles */
+
+/* General math container */
+.math-content {
+ font-size: 1rem;
+ line-height: 1.6;
+}
+
+/* Inline math */
+.math-inline {
+ display: inline-block;
+ vertical-align: middle;
+}
+
+/* Block math */
+.math-block {
+ display: block;
+ margin: 1rem 0;
+ overflow-x: auto;
+ text-align: center;
+}
+
+/* Math editor toolbar */
+.math-symbols-toolbar {
+ background-color: #f7f7f7;
+ border-radius: 6px;
+ padding: 0.75rem;
+ margin-top: 0.5rem;
+ -webkit-box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
+}
+
+.math-symbols-toolbar button {
+ margin-right: 0.25rem;
+ margin-bottom: 0.25rem;
+ -webkit-transition: all 0.2s ease;
+ -o-transition: all 0.2s ease;
+ transition: all 0.2s ease;
+}
+
+.math-symbols-toolbar button:hover {
+ background-color: #6e44ff;
+ color: white;
+}
+
+/* Math examples section */
+.math-examples {
+ background-color: #f8f9fa;
+ border-radius: 6px;
+ padding: 0.75rem;
+ margin-top: 0.5rem;
+ border: 1px solid #e9ecef;
+}
+
+.math-examples table {
+ margin-bottom: 0;
+}
+
+.math-examples th,
+.math-examples td {
+ padding: 0.4rem 0.5rem;
+ vertical-align: middle;
+}
+
+.math-examples code {
+ background-color: rgba(110, 68, 255, 0.1);
+ color: #6e44ff;
+ padding: 0.2rem 0.4rem;
+ border-radius: 4px;
+}
+
+/* Question option styling */
+.option-content {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ max-width: calc(100% - 60px);
+}
+
+/* Short answer styling */
+.short-answer-content {
+ background-color: rgba(0, 199, 164, 0.05);
+ border: 1px solid #00c7a4;
+ border-radius: 6px;
+ padding: 1rem;
+}
+
+/* Katex specific overrides */
+.katex {
+ font-size: 1.1em;
+}
+
+.katex-display {
+ overflow-x: auto;
+ overflow-y: hidden;
+ padding: 0.5rem 0;
+}
+
+/* Preview mode styling */
+.preview-container {
+ min-height: 100px;
+ background-color: #fff;
+ border: 1px solid #dbdbdb;
+ border-radius: 6px;
+ padding: 1rem;
+ -webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.05);
+ box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.05);
+}
+
+/* Tabs styling */
+.tabs ul {
+ border-bottom-color: #dbdbdb;
+}
+
+.tabs li.is-active a {
+ border-bottom-color: #6e44ff;
+ color: #6e44ff;
+}
+
+/* Textarea focus styling */
+#math-editor-textarea:focus {
+ border-color: #6e44ff;
+ -webkit-box-shadow: 0 0 0 0.125em rgba(110, 68, 255, 0.25);
+ box-shadow: 0 0 0 0.125em rgba(110, 68, 255, 0.25);
+}
diff --git a/src/assets/react.svg b/src/assets/react.svg
deleted file mode 100644
index 6c87de9..0000000
--- a/src/assets/react.svg
+++ /dev/null
@@ -1 +0,0 @@
-
\ No newline at end of file
diff --git a/src/assets/studentProfile.css b/src/assets/studentProfile.css
new file mode 100644
index 0000000..c0b26e1
--- /dev/null
+++ b/src/assets/studentProfile.css
@@ -0,0 +1,781 @@
+/*
+* Prefixed by https://autoprefixer.github.io
+* PostCSS: v8.4.14,
+* Autoprefixer: v10.4.7
+* Browsers: last 4 version
+*/
+
+/* Student Profile Custom Styles - Unconventional Design */
+
+/* Container */
+.student-profile-container {
+ max-width: 1400px;
+ margin: 0 auto;
+ padding: 2rem 1rem;
+ overflow-x: hidden;
+}
+
+/* Back Button */
+.back-button-container {
+ margin-bottom: 2rem;
+ position: relative;
+ z-index: 10;
+}
+
+/* Hero Section */
+.student-profile-hero {
+ background: -o-linear-gradient(315deg, #6e44ff 0%, #9f84ff 100%);
+ background: linear-gradient(135deg, #6e44ff 0%, #9f84ff 100%);
+ border-radius: 0;
+ padding: 0;
+ margin-bottom: 3rem;
+ position: relative;
+ overflow: hidden;
+ color: white;
+ min-height: 400px;
+ -webkit-box-shadow: 0 15px 30px rgba(110, 68, 255, 0.2);
+ box-shadow: 0 15px 30px rgba(110, 68, 255, 0.2);
+}
+
+.student-profile-hero::before {
+ content: "";
+ position: absolute;
+ top: 0;
+ left: 0;
+ width: 100%;
+ height: 100%;
+ background-image: url("data:image/svg+xml,%3Csvg width='100' height='100' viewBox='0 0 100 100' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M11 18c3.866 0 7-3.134 7-7s-3.134-7-7-7-7 3.134-7 7 3.134 7 7 7zm48 25c3.866 0 7-3.134 7-7s-3.134-7-7-7-7 3.134-7 7 3.134 7 7 7zm-43-7c1.657 0 3-1.343 3-3s-1.343-3-3-3-3 1.343-3 3 1.343 3 3 3zm63 31c1.657 0 3-1.343 3-3s-1.343-3-3-3-3 1.343-3 3 1.343 3 3 3zM34 90c1.657 0 3-1.343 3-3s-1.343-3-3-3-3 1.343-3 3 1.343 3 3 3zm56-76c1.657 0 3-1.343 3-3s-1.343-3-3-3-3 1.343-3 3 1.343 3 3 3zM12 86c2.21 0 4-1.79 4-4s-1.79-4-4-4-4 1.79-4 4 1.79 4 4 4zm28-65c2.21 0 4-1.79 4-4s-1.79-4-4-4-4 1.79-4 4 1.79 4 4 4zm23-11c2.76 0 5-2.24 5-5s-2.24-5-5-5-5 2.24-5 5 2.24 5 5 5zm-6 60c2.21 0 4-1.79 4-4s-1.79-4-4-4-4 1.79-4 4 1.79 4 4 4zm29 22c2.76 0 5-2.24 5-5s-2.24-5-5-5-5 2.24-5 5 2.24 5 5 5zM32 63c2.76 0 5-2.24 5-5s-2.24-5-5-5-5 2.24-5 5 2.24 5 5 5zm57-13c2.76 0 5-2.24 5-5s-2.24-5-5-5-5 2.24-5 5 2.24 5 5 5zm-9-21c1.105 0 2-.895 2-2s-.895-2-2-2-2 .895-2 2 .895 2 2 2zM60 91c1.105 0 2-.895 2-2s-.895-2-2-2-2 .895-2 2 .895 2 2 2zM35 41c1.105 0 2-.895 2-2s-.895-2-2-2-2 .895-2 2 .895 2 2 2zM12 60c1.105 0 2-.895 2-2s-.895-2-2-2-2 .895-2 2 .895 2 2 2z' fill='%23ffffff' fill-opacity='0.1' fill-rule='evenodd'/%3E%3C/svg%3E");
+ opacity: 0.5;
+}
+
+.hero-content {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 3rem 2rem;
+ position: relative;
+ z-index: 2;
+}
+
+.student-info {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ padding-right: 2rem;
+}
+
+.hero-illustration {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: end;
+ -ms-flex-pack: end;
+ justify-content: flex-end;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ position: relative;
+}
+
+.hero-illustration img {
+ max-width: 100%;
+ max-height: 350px;
+ -webkit-transform: scale(1.2) translateY(-20px);
+ -ms-transform: scale(1.2) translateY(-20px);
+ transform: scale(1.2) translateY(-20px);
+ -webkit-filter: drop-shadow(0 10px 15px rgba(0, 0, 0, 0.2));
+ filter: drop-shadow(0 10px 15px rgba(0, 0, 0, 0.2));
+}
+
+/* Student Profile Elements */
+.student-profile-avatar {
+ width: 120px;
+ height: 120px;
+ border-radius: 0;
+ border: 4px solid white;
+ -webkit-box-shadow: 0 4px 10px rgba(0, 0, 0, 0.1);
+ box-shadow: 0 4px 10px rgba(0, 0, 0, 0.1);
+ margin-bottom: 1.5rem;
+}
+
+.student-profile-name {
+ font-size: 2.5rem;
+ font-weight: 700;
+ margin-bottom: 0.5rem;
+}
+
+.student-profile-email {
+ font-size: 1.1rem;
+ opacity: 0.9;
+ margin-bottom: 1rem;
+}
+
+.student-profile-tags {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ margin-bottom: 1.5rem;
+}
+
+.student-profile-tag {
+ background-color: rgba(255, 255, 255, 0.2);
+ color: white;
+ border-radius: 0;
+ padding: 0.3rem 1rem;
+ margin-right: 0.5rem;
+ font-weight: 500;
+}
+
+.student-profile-tag.is-active {
+ background-color: #00c7a4;
+}
+
+.student-profile-tag.is-inactive {
+ background-color: #ff2c73;
+}
+
+.student-profile-tag.is-suspended {
+ background-color: #ffa500;
+}
+
+.student-meta {
+ margin-top: 1.5rem;
+}
+
+.student-meta-item {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin-bottom: 0.5rem;
+}
+
+.student-meta-item .icon {
+ margin-right: 0.5rem;
+}
+
+/* Main Content Layout */
+.student-profile-main {
+ display: -ms-grid;
+ display: grid;
+ -ms-grid-columns: 1fr 2rem 2fr;
+ grid-template-columns: 1fr 2fr;
+ gap: 2rem;
+ margin-top: 2rem;
+}
+
+/* Sections */
+.student-profile-section {
+ background-color: white;
+ border-radius: 0;
+ -webkit-box-shadow: 0 4px 20px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 4px 20px rgba(0, 0, 0, 0.05);
+ padding: 1.5rem;
+ margin-bottom: 2rem;
+ position: relative;
+ overflow: hidden;
+ -webkit-transition: -webkit-transform 0.3s ease, -webkit-box-shadow 0.3s ease;
+ transition: -webkit-transform 0.3s ease, -webkit-box-shadow 0.3s ease;
+ -o-transition: transform 0.3s ease, box-shadow 0.3s ease;
+ transition: transform 0.3s ease, box-shadow 0.3s ease;
+ transition: transform 0.3s ease, box-shadow 0.3s ease,
+ -webkit-transform 0.3s ease, -webkit-box-shadow 0.3s ease;
+}
+
+.student-profile-section:hover {
+ -webkit-transform: translateY(-5px);
+ -ms-transform: translateY(-5px);
+ transform: translateY(-5px);
+ -webkit-box-shadow: 0 8px 30px rgba(0, 0, 0, 0.1);
+ box-shadow: 0 8px 30px rgba(0, 0, 0, 0.1);
+}
+
+.student-profile-section-title {
+ font-size: 1.5rem;
+ font-weight: 700;
+ margin-bottom: 1.5rem;
+ color: #333;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.student-profile-section-title::after {
+ content: "";
+ -webkit-box-flex: 1;
+ -ms-flex-positive: 1;
+ flex-grow: 1;
+ height: 2px;
+ background-color: #f0f0f0;
+ margin-left: 1rem;
+}
+
+/* Statistics Section */
+.stats-section {
+ position: relative;
+ overflow: hidden;
+}
+
+.stats-illustration-container {
+ position: absolute;
+ top: -20px;
+ right: -20px;
+ opacity: 0.1;
+ z-index: 0;
+ -webkit-transform: rotate(10deg);
+ -ms-transform: rotate(10deg);
+ transform: rotate(10deg);
+}
+
+.stats-illustration {
+ width: 150px;
+ height: auto;
+}
+
+/* Performance Overview */
+.performance-overview {
+ margin-bottom: 1.5rem;
+ position: relative;
+ z-index: 1;
+}
+
+.performance-header {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin-bottom: 1rem;
+}
+
+.performance-title {
+ font-size: 1.2rem;
+ font-weight: 600;
+ color: #333;
+}
+
+.performance-badge {
+ background-color: #6e44ff;
+ color: white;
+ padding: 0.3rem 1rem;
+ font-weight: 600;
+ font-size: 0.9rem;
+ border-radius: 0;
+}
+
+/* Stats Grid */
+.stats-grid {
+ display: -ms-grid;
+ display: grid;
+ grid-template-columns: repeat(auto-fit, minmax(120px, 1fr));
+ gap: 1rem;
+ position: relative;
+ z-index: 1;
+ margin-bottom: 2rem;
+}
+
+.student-profile-stat {
+ text-align: center;
+ padding: 1.5rem;
+ background-color: #f9f9f9;
+ border-radius: 0;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+}
+
+.student-profile-stat:hover {
+ background-color: #6e44ff;
+ color: white;
+ -webkit-transform: translateY(-5px);
+ -ms-transform: translateY(-5px);
+ transform: translateY(-5px);
+}
+
+.student-profile-stat:hover .student-profile-stat-value,
+.student-profile-stat:hover .student-profile-stat-label,
+.student-profile-stat:hover .stat-trend {
+ color: white;
+}
+
+.student-profile-stat-value {
+ font-size: 2.5rem;
+ font-weight: 700;
+ color: #6e44ff;
+ line-height: 1;
+ margin-bottom: 0.5rem;
+}
+
+.student-profile-stat-label {
+ font-size: 0.9rem;
+ color: #666;
+ text-transform: uppercase;
+ letter-spacing: 1px;
+ font-weight: 600;
+ margin-bottom: 0.5rem;
+}
+
+.stat-trend {
+ font-size: 0.8rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ gap: 0.25rem;
+}
+
+.stat-trend.positive {
+ color: #00c7a4;
+}
+
+.stat-trend.negative {
+ color: #ff2c73;
+}
+
+.stat-trend.neutral {
+ color: #999;
+}
+
+/* Subject Performance */
+.subject-performance {
+ position: relative;
+ z-index: 1;
+}
+
+.subject-performance-title {
+ font-size: 1.2rem;
+ font-weight: 600;
+ color: #333;
+ margin-bottom: 1rem;
+}
+
+.subject-cards {
+ display: -ms-grid;
+ display: grid;
+ grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
+ gap: 1rem;
+}
+
+.subject-card {
+ background-color: white;
+ border: 1px solid #f0f0f0;
+ -webkit-box-shadow: 0 4px 10px rgba(0, 0, 0, 0.05);
+ box-shadow: 0 4px 10px rgba(0, 0, 0, 0.05);
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+ overflow: hidden;
+}
+
+.subject-card:hover {
+ -webkit-transform: translateY(-5px);
+ -ms-transform: translateY(-5px);
+ transform: translateY(-5px);
+ -webkit-box-shadow: 0 8px 15px rgba(0, 0, 0, 0.1);
+ box-shadow: 0 8px 15px rgba(0, 0, 0, 0.1);
+}
+
+.subject-card-header {
+ background-color: #6e44ff;
+ color: white;
+ padding: 0.75rem 1rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: justify;
+ -ms-flex-pack: justify;
+ justify-content: space-between;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.subject-card-label {
+ font-weight: 600;
+ font-size: 1rem;
+}
+
+.subject-card-score {
+ font-weight: 700;
+ font-size: 1.2rem;
+}
+
+.subject-card-body {
+ padding: 1rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+}
+
+.subject-card-icon {
+ width: 40px;
+ height: 40px;
+ background-color: rgba(110, 68, 255, 0.1);
+ border-radius: 0;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ margin-right: 1rem;
+ color: #6e44ff;
+ font-size: 1.2rem;
+}
+
+.subject-card-info {
+ -webkit-box-flex: 1;
+ -ms-flex: 1;
+ flex: 1;
+}
+
+.subject-card-trend {
+ font-size: 0.9rem;
+ font-weight: 600;
+ margin-bottom: 0.25rem;
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ gap: 0.25rem;
+}
+
+.subject-card-trend.positive {
+ color: #00c7a4;
+}
+
+.subject-card-trend.negative {
+ color: #ff2c73;
+}
+
+.subject-card-trend.neutral {
+ color: #999;
+}
+
+.subject-card-status {
+ font-size: 0.8rem;
+ color: #666;
+ text-transform: uppercase;
+ letter-spacing: 1px;
+}
+
+/* Settings Section */
+.settings-section {
+ margin-top: 2rem;
+}
+
+.settings-content {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+}
+
+.settings-illustration-container {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ margin-bottom: 1.5rem;
+}
+
+.settings-illustration {
+ max-width: 100%;
+ height: 150px;
+}
+
+/* Practice Sheets Section */
+.practice-sheets-section {
+ position: relative;
+}
+
+.practice-sheets-content {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+}
+
+.practice-illustration-container {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ margin-bottom: 1.5rem;
+}
+
+.practice-illustration {
+ height: 120px;
+ width: auto;
+}
+
+.practice-sheets-table-container {
+ position: relative;
+ z-index: 1;
+}
+
+/* Activity Section */
+.activity-section {
+ position: relative;
+}
+
+.activity-content {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+}
+
+.activity-illustration-container {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ margin-bottom: 1.5rem;
+}
+
+.activity-illustration {
+ height: 120px;
+ width: auto;
+}
+
+.activity-timeline-container {
+ position: relative;
+ z-index: 1;
+}
+
+.activity-timeline {
+ position: relative;
+ padding-left: 2rem;
+}
+
+.activity-timeline::before {
+ content: "";
+ position: absolute;
+ top: 0;
+ left: 8px;
+ height: 100%;
+ width: 2px;
+ background-color: #f0f0f0;
+}
+
+.activity-item {
+ position: relative;
+ padding-bottom: 1.5rem;
+}
+
+.activity-item:last-child {
+ padding-bottom: 0;
+}
+
+.activity-marker {
+ position: absolute;
+ left: -2rem;
+ top: 0;
+ width: 18px;
+ height: 18px;
+ border-radius: 0;
+ background-color: #6e44ff;
+ border: 3px solid white;
+ -webkit-box-shadow: 0 0 0 2px #f0f0f0;
+ box-shadow: 0 0 0 2px #f0f0f0;
+ z-index: 1;
+}
+
+.activity-marker.is-success {
+ background-color: #00c7a4;
+}
+
+.activity-marker.is-warning {
+ background-color: #ffd166;
+}
+
+.activity-date {
+ font-size: 0.8rem;
+ color: #999;
+ margin-bottom: 0.25rem;
+ font-weight: 500;
+}
+
+.activity-content {
+ font-weight: 500;
+ color: #333;
+}
+
+.activity-score {
+ font-weight: 700;
+ color: #6e44ff;
+}
+
+/* Illustration Sections */
+.math-illustration-section,
+.study-illustration-section {
+ display: -webkit-box;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ -webkit-box-align: center;
+ -ms-flex-align: center;
+ align-items: center;
+ padding: 2rem;
+ background-color: #f9f9f9;
+ min-height: 300px;
+}
+
+.math-illustration,
+.study-illustration {
+ max-width: 100%;
+ max-height: 250px;
+ -webkit-filter: drop-shadow(0 10px 15px rgba(0, 0, 0, 0.1));
+ filter: drop-shadow(0 10px 15px rgba(0, 0, 0, 0.1));
+}
+
+/* Button Styles */
+.hip-button {
+ background-color: #6e44ff;
+ color: white;
+ border: none;
+ border-radius: 0;
+ padding: 0.5rem 1.5rem;
+ font-weight: 600;
+ -webkit-transition: all 0.3s ease;
+ -o-transition: all 0.3s ease;
+ transition: all 0.3s ease;
+ -webkit-box-shadow: 0 4px 10px rgba(110, 68, 255, 0.3);
+ box-shadow: 0 4px 10px rgba(110, 68, 255, 0.3);
+}
+
+.hip-button:hover {
+ background-color: #5a36d5;
+ -webkit-transform: translateY(-2px);
+ -ms-transform: translateY(-2px);
+ transform: translateY(-2px);
+ -webkit-box-shadow: 0 6px 15px rgba(110, 68, 255, 0.4);
+ box-shadow: 0 6px 15px rgba(110, 68, 255, 0.4);
+ color: white;
+}
+
+.hip-button.is-small {
+ padding: 0.25rem 0.75rem;
+ font-size: 0.85rem;
+}
+
+/* Responsive Styles */
+@media screen and (max-width: 1200px) {
+ .student-profile-main {
+ -ms-grid-columns: 1fr;
+ grid-template-columns: 1fr;
+ }
+
+ .hero-content {
+ -webkit-box-orient: vertical;
+ -webkit-box-direction: normal;
+ -ms-flex-direction: column;
+ flex-direction: column;
+ text-align: center;
+ }
+
+ .student-info {
+ padding-right: 0;
+ margin-bottom: 2rem;
+ }
+
+ .student-profile-tags {
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ }
+
+ .student-meta {
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ }
+
+ .student-meta-item {
+ -webkit-box-pack: center;
+ -ms-flex-pack: center;
+ justify-content: center;
+ }
+}
+
+@media screen and (max-width: 768px) {
+ .student-profile-hero {
+ min-height: auto;
+ }
+
+ .hero-content {
+ padding: 2rem 1rem;
+ }
+
+ .student-profile-name {
+ font-size: 2rem;
+ }
+
+ .student-profile-avatar {
+ width: 100px;
+ height: 100px;
+ }
+
+ .hero-illustration img {
+ max-height: 200px;
+ }
+
+ .math-illustration-section,
+ .study-illustration-section {
+ min-height: 200px;
+ }
+
+ .math-illustration,
+ .study-illustration {
+ max-height: 180px;
+ }
+}
diff --git a/src/components/ProtectedRoute.tsx b/src/components/ProtectedRoute.tsx
new file mode 100644
index 0000000..737032b
--- /dev/null
+++ b/src/components/ProtectedRoute.tsx
@@ -0,0 +1,13 @@
+import { Navigate, Outlet, useLocation } from "react-router-dom";
+import { useAuthStore } from "../stores/authStore";
+
+export const ProtectedRoute = () => {
+ const isAuthenticated = useAuthStore((state) => state.isAuthenticated);
+ const location = useLocation();
+
+ if (!isAuthenticated) {
+ return ;
+ }
+
+ return ;
+};
diff --git a/src/index.css b/src/index.css
index a461c50..bd23856 100644
--- a/src/index.css
+++ b/src/index.css
@@ -1 +1,161 @@
-@import "tailwindcss";
\ No newline at end of file
+@import "tailwindcss";
+
+/* ================================
+ Satoshi Font Family
+ ================================ */
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Light.woff2") format("woff2");
+ font-weight: 300;
+ font-style: normal;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-LightItalic.woff2") format("woff2");
+ font-weight: 300;
+ font-style: italic;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Regular.woff2") format("woff2");
+ font-weight: 400;
+ font-style: normal;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Italic.woff2") format("woff2");
+ font-weight: 400;
+ font-style: italic;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Medium.woff2") format("woff2");
+ font-weight: 500;
+ font-style: normal;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-MediumItalic.woff2") format("woff2");
+ font-weight: 500;
+ font-style: italic;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Bold.woff2") format("woff2");
+ font-weight: 700;
+ font-style: normal;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-BoldItalic.woff2") format("woff2");
+ font-weight: 700;
+ font-style: italic;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-Black.woff2") format("woff2");
+ font-weight: 900;
+ font-style: normal;
+ font-display: swap;
+}
+
+@font-face {
+ font-family: "Satoshi";
+ src: url("./assets/fonts/Satoshi-BlackItalic.woff2") format("woff2");
+ font-weight: 900;
+ font-style: italic;
+ font-display: swap;
+}
+
+@theme {
+ --font-satoshi: "Satoshi", system-ui, sans-serif;
+}
+
+@layer utilities {
+ /* Base family */
+ .font-satoshi {
+ font-family: var(--font-satoshi);
+ }
+
+ /* Light */
+ .font-satoshi-light {
+ font-family: var(--font-satoshi);
+ font-weight: 300;
+ font-style: normal;
+ }
+
+ .font-satoshi-light-italic {
+ font-family: var(--font-satoshi);
+ font-weight: 300;
+ font-style: italic;
+ }
+
+ /* Regular */
+ .font-satoshi-regular {
+ font-family: var(--font-satoshi);
+ font-weight: 400;
+ font-style: normal;
+ }
+
+ .font-satoshi-italic {
+ font-family: var(--font-satoshi);
+ font-weight: 400;
+ font-style: italic;
+ }
+
+ /* Medium */
+ .font-satoshi-medium {
+ font-family: var(--font-satoshi);
+ font-weight: 500;
+ font-style: normal;
+ }
+
+ .font-satoshi-medium-italic {
+ font-family: var(--font-satoshi);
+ font-weight: 500;
+ font-style: italic;
+ }
+
+ /* Bold */
+ .font-satoshi-bold {
+ font-family: var(--font-satoshi);
+ font-weight: 700;
+ font-style: normal;
+ }
+
+ .font-satoshi-bold-italic {
+ font-family: var(--font-satoshi);
+ font-weight: 700;
+ font-style: italic;
+ }
+
+ /* Black */
+ .font-satoshi-black {
+ font-family: var(--font-satoshi);
+ font-weight: 900;
+ font-style: normal;
+ }
+
+ .font-satoshi-black-italic {
+ font-family: var(--font-satoshi);
+ font-weight: 900;
+ font-style: italic;
+ }
+}
diff --git a/src/pages/Login.tsx b/src/pages/Login.tsx
new file mode 100644
index 0000000..04b30f5
--- /dev/null
+++ b/src/pages/Login.tsx
@@ -0,0 +1,157 @@
+import { useState, useEffect } from "react";
+import type { FormEvent } from "react";
+import { useNavigate, useLocation } from "react-router-dom";
+import { useAuthStore } from "../stores/authStore";
+
+interface LocationState {
+ from?: {
+ pathname: string;
+ };
+}
+
+export const Login = () => {
+ const [email, setEmail] = useState("");
+ const [password, setPassword] = useState("");
+ const navigate = useNavigate();
+ const location = useLocation();
+
+ const { login, isAuthenticated, isLoading, error, clearError } =
+ useAuthStore();
+
+ const from = (location.state as LocationState)?.from?.pathname || "/student";
+
+ // Redirect if already authenticated
+ useEffect(() => {
+ if (isAuthenticated) {
+ navigate("/student", { replace: true });
+ }
+ }, [isAuthenticated, navigate]);
+
+ // Clear error when component unmounts or inputs change
+ useEffect(() => {
+ return () => clearError();
+ }, [clearError]);
+
+ const handleSubmit = async (e: FormEvent) => {
+ e.preventDefault();
+ clearError();
+
+ const success = await login({ email, password });
+ if (success) {
+ navigate(from, { replace: true });
+ }
+ };
+
+ // Don't render login form if already authenticated
+ if (isAuthenticated) {
+ return null;
+ }
+
+ return (
+
+
+
+

+
+
+ Welcome Back
+
+
+
+
+ setEmail(e.target.value)}
+ disabled={isLoading}
+ className="w-full px-4 py-3 border border-gray-300 rounded-lg focus:ring-2 focus:ring-indigo-500 focus:border-transparent outline-none transition disabled:bg-gray-100 disabled:cursor-not-allowed"
+ placeholder="Enter your email"
+ />
+
+
+
+
+ {error && (
+
+ {error}
+
+ )}
+
+
+
+
+
+ );
+};
diff --git a/src/pages/StudentDashboard.tsx b/src/pages/StudentDashboard.tsx
new file mode 100644
index 0000000..cd677a7
--- /dev/null
+++ b/src/pages/StudentDashboard.tsx
@@ -0,0 +1,62 @@
+import { useNavigate } from "react-router-dom";
+import { useAuthStore } from "../stores/authStore";
+
+export const StudentDashboard = () => {
+ const user = useAuthStore((state) => state.user);
+ const logout = useAuthStore((state) => state.logout);
+ const navigate = useNavigate();
+
+ const handleLogout = () => {
+ logout();
+ navigate("/login");
+ };
+
+ return (
+
+
+
+
+
+
Dashboard
+
+
Email: {user?.email}
+
Role: {user?.role}
+
Status: {user?.status}
+
+ Member since:{" "}
+ {user?.joined_at
+ ? new Date(user.joined_at).toLocaleDateString()
+ : "N/A"}
+
+
+
+
+
+ );
+};
diff --git a/src/stores/authStore.ts b/src/stores/authStore.ts
new file mode 100644
index 0000000..94309bf
--- /dev/null
+++ b/src/stores/authStore.ts
@@ -0,0 +1,75 @@
+import { create } from "zustand";
+import { persist } from "zustand/middleware";
+import { api, type User, type LoginRequest } from "../utils/api";
+
+interface AuthState {
+ user: User | null;
+ token: string | null;
+ isAuthenticated: boolean;
+ isLoading: boolean;
+ error: string | null;
+ login: (credentials: LoginRequest) => Promise;
+ logout: () => void;
+ clearError: () => void;
+}
+
+export const useAuthStore = create()(
+ persist(
+ (set) => ({
+ user: null,
+ token: null,
+ isAuthenticated: false,
+ isLoading: false,
+ error: null,
+
+ login: async (credentials: LoginRequest) => {
+ set({ isLoading: true, error: null });
+
+ try {
+ const response = await api.login(credentials);
+
+ set({
+ user: response.user,
+ token: response.token,
+ isAuthenticated: true,
+ isLoading: false,
+ error: null,
+ });
+
+ return true;
+ } catch (error) {
+ const errorMessage =
+ error instanceof Error ? error.message : "Login failed";
+ set({
+ user: null,
+ token: null,
+ isAuthenticated: false,
+ isLoading: false,
+ error: errorMessage,
+ });
+
+ return false;
+ }
+ },
+
+ logout: () => {
+ set({
+ user: null,
+ token: null,
+ isAuthenticated: false,
+ error: null,
+ });
+ },
+
+ clearError: () => set({ error: null }),
+ }),
+ {
+ name: "auth-storage",
+ partialize: (state) => ({
+ user: state.user,
+ token: state.token,
+ isAuthenticated: state.isAuthenticated,
+ }),
+ }
+ )
+);
diff --git a/src/utils/api.ts b/src/utils/api.ts
new file mode 100644
index 0000000..4660407
--- /dev/null
+++ b/src/utils/api.ts
@@ -0,0 +1,101 @@
+const API_URL = "https://dsat-api.edbridgescholars.com";
+
+export interface LoginRequest {
+ email: string;
+ password: string;
+}
+
+export interface User {
+ email: string;
+ name: string;
+ role: "STUDENT" | "TEACHER" | "ADMIN";
+ avatar_url: string;
+ id: string;
+ status: "ACTIVE" | "INACTIVE";
+ joined_at: string;
+ last_active: string;
+}
+
+export interface LoginResponse {
+ token: string;
+ token_type: string;
+ user: User;
+}
+
+export interface ApiError {
+ detail?: string;
+ message?: string;
+}
+
+class ApiClient {
+ private baseURL: string;
+
+ constructor(baseURL: string) {
+ this.baseURL = baseURL;
+ }
+
+ private async request(
+ endpoint: string,
+ options: RequestInit = {}
+ ): Promise {
+ const url = `${this.baseURL}${endpoint}`;
+
+ const config: RequestInit = {
+ ...options,
+ headers: {
+ "Content-Type": "application/json",
+ ...options.headers,
+ },
+ };
+
+ try {
+ const response = await fetch(url, config);
+
+ if (!response.ok) {
+ const error: ApiError = await response.json().catch(() => ({
+ message: "An error occurred",
+ }));
+ throw new Error(error.detail || error.message || "Request failed");
+ }
+
+ return await response.json();
+ } catch (error) {
+ if (error instanceof Error) {
+ throw error;
+ }
+ throw new Error("Network error occurred");
+ }
+ }
+
+ // Auth endpoints
+ async login(credentials: LoginRequest): Promise {
+ return this.request("/auth/login/", {
+ method: "POST",
+ body: JSON.stringify(credentials),
+ });
+ }
+
+ // Authenticated request helper
+ async authenticatedRequest(
+ endpoint: string,
+ token: string,
+ options: RequestInit = {}
+ ): Promise {
+ return this.request(endpoint, {
+ ...options,
+ headers: {
+ ...options.headers,
+ Authorization: `Bearer ${token}`,
+ },
+ });
+ }
+
+ // Example: Get user profile (authenticated endpoint)
+ async getUserProfile(token: string): Promise {
+ return this.authenticatedRequest("/auth/me", token);
+ }
+
+ // Add more API methods here as needed
+}
+
+export const api = new ApiClient(API_URL);