TheFrogGod commited on
Commit
03cf0e2
·
1 Parent(s): caaee88

Restart: updated profile styling

Browse files
Files changed (2) hide show
  1. web/profile.html +259 -144
  2. web/style.css +246 -0
web/profile.html CHANGED
@@ -6,69 +6,131 @@
6
  <title>Profile - CTRL + ALT + HEAL</title>
7
  <script src="https://cdn.tailwindcss.com"></script>
8
  <script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
 
9
  </head>
10
- <body class="bg-[#F7F8F9] text-gray-800 min-h-screen">
11
- <!-- Navbar -->
12
- <nav class="bg-white border border-gray-200 px-6 py-4 mb-6">
13
- <div class="container mx-auto flex justify-between items-center">
14
- <a href="index.html" class="text-2xl font-bold text-[#6B9080]"
15
- >CTRL + ALT + HEAL</a
 
 
 
 
16
  >
17
- <ul class="flex space-x-6 text-sm font-medium text-gray-700">
18
- <li><a href="index.html" class="hover:text-[#6B9080]">Home</a></li>
19
- <li>
20
- <a href="analyzer.html" class="hover:text-[#6B9080]">Analyzer</a>
21
- </li>
22
- <li>
23
- <a href="profile.html" class="hover:text-[#6B9080]">Profile</a>
24
- </li>
25
- <li><button onclick="logout()" class="text-red-500">Logout</button></li>
26
  </ul>
 
 
 
 
 
 
 
 
27
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
28
  </nav>
29
 
30
- <div class="container mx-auto px-6">
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
31
  <!-- VIEW MODE -->
32
  <div id="profileViewSection">
33
  <div class="flex items-start space-x-6 mb-10">
34
  <!-- Avatar & Edit Button -->
35
  <div class="flex flex-col items-center">
36
  <div class="w-32 h-32 bg-gray-300 rounded-full"></div>
37
- <button
38
- id="editProfileBtn"
39
- class="mt-2 bg-[#6B9080] text-white px-4 py-2 rounded hover:bg-[#5b7e6a] transition"
40
- >
41
  Edit Profile
42
  </button>
43
  <a href="analyzer.html"
44
- ><button
45
- class="mt-2 bg-[#6B9080] text-white px-4 py-2 rounded hover:bg-[#5b7e6a] transition"
46
- >
47
  Go To Analyzer
48
- </button>
49
- </a>
50
  </div>
51
 
52
-
53
-
54
  <!-- User Info -->
55
  <div>
56
- <h1 class="text-3xl font-semibold text-gray-800 mb-4">
57
- Your Profile
58
- </h1>
59
- <p class="text-gray-700 mb-2">
60
  Name: <span id="userName" class="font-medium">Loading...</span>
61
  </p>
62
- <p class="text-gray-700 mb-2">
63
- DOB: <span id="userDOB" class="font-medium">Loding...</span>
64
  </p>
65
- <!-- <p class="text-gray-700 mb-2">
66
- Big Things We Should Fix:
67
- <span id="userFix" class="font-medium"></span>
68
- </p>
69
- <p class="text-gray-700 mb-6">
70
- Health Goals: <span id="userGoals" class="font-medium"></span>
71
- </p> -->
72
  </div>
73
  </div>
74
  </div>
@@ -76,53 +138,38 @@
76
  <!-- EDIT MODE -->
77
  <div id="profileEditSection" class="hidden mb-10">
78
  <div class="flex flex-col sm:flex-row items-start space-x-6">
79
- <!-- Avatar Placeholder -->
80
  <div class="flex flex-col items-center mb-4 sm:mb-0">
81
  <div class="w-32 h-32 bg-gray-300 rounded-full"></div>
82
  </div>
83
- <!-- Edit Form -->
84
  <div class="flex-1">
85
- <h1 class="text-3xl font-semibold text-gray-800 mb-4">
86
- Edit Profile
87
- </h1>
88
  <div class="space-y-4">
89
  <div>
90
- <label
91
- for="inputName"
92
- class="block text-sm font-medium text-gray-600"
93
  >Name</label
94
  >
95
  <input
96
  type="text"
97
  id="inputName"
98
- class="w-full border border-gray-300 rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
99
  />
100
  </div>
101
  <div>
102
- <label
103
- for="inputDOB"
104
- class="block text-sm font-medium text-gray-600"
105
  >Date of Birth</label
106
  >
107
  <input
108
  type="date"
109
  id="inputDOB"
110
- class="w-full border border-gray-300 rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
111
  />
112
  </div>
113
- </div>
114
  </div>
115
  <div class="flex space-x-2 mt-4">
116
- <button
117
- id="saveProfileBtn"
118
- class="bg-[#6B9080] text-white px-4 py-2 rounded hover:bg-[#5b7e6a] transition"
119
- >
120
  Save
121
  </button>
122
- <button
123
- id="cancelProfileBtn"
124
- class="bg-gray-300 text-gray-700 px-4 py-2 rounded hover:bg-gray-400 transition"
125
- >
126
  Cancel
127
  </button>
128
  </div>
@@ -130,25 +177,18 @@
130
  </div>
131
  </div>
132
 
133
-
134
  <!-- Chart Section -->
135
  <div class="mt-10" id="chartSection">
136
- <!-- Card Wrapper -->
137
  <div class="bg-white border border-gray-200 rounded-lg p-6 mb-6">
138
- <h2 class="text-xl font-semibold text-gray-800 mb-4">
139
- Health Progress
140
- </h2>
141
-
142
- <!-- Controls Row -->
143
  <div
144
  class="flex flex-col sm:flex-row sm:items-center sm:justify-between gap-4 mb-6"
145
  >
146
- <!-- Date & Score Inputs -->
147
  <div class="flex flex-1 gap-2">
148
  <input
149
  type="date"
150
  id="entryDate"
151
- class="flex-1 border border-gray-300 rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
152
  />
153
  <input
154
  type="number"
@@ -156,27 +196,18 @@
156
  min="0"
157
  max="100"
158
  placeholder="Score"
159
- class="w-24 border border-gray-300 rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
160
  />
161
  </div>
162
- <!-- Buttons -->
163
  <div class="flex gap-2">
164
- <button
165
- id="addEntryBtn"
166
- class="bg-[#6B9080] text-white px-4 py-2 rounded hover:bg-[#5b7e6a] transition"
167
- >
168
  Add Entry
169
  </button>
170
- <button
171
- id="resetChartBtn"
172
- class="bg-red-500 text-white px-4 py-2 rounded hover:bg-red-600 transition"
173
- >
174
  Reset Chart
175
  </button>
176
  </div>
177
  </div>
178
-
179
- <!-- Chart Canvas -->
180
  <div class="overflow-x-auto">
181
  <canvas id="progressChart" class="w-full h-64"></canvas>
182
  </div>
@@ -185,55 +216,127 @@
185
  </div>
186
 
187
  <script type="module">
188
- import { initializeApp } from 'https://www.gstatic.com/firebasejs/9.22.0/firebase-app.js';
189
- import { getAuth, onAuthStateChanged, signOut } from 'https://www.gstatic.com/firebasejs/9.22.0/firebase-auth.js';
190
- import { getFirestore, doc, getDoc, updateDoc } from 'https://www.gstatic.com/firebasejs/9.22.0/firebase-firestore.js';
191
-
 
 
 
 
 
 
 
 
 
 
 
 
 
192
  const firebaseConfig = {
193
  apiKey: "AIzaSyAPhM_Ee7cLzyKHs5zyFy8g5ZOk9-pubRI",
194
  authDomain: "login-tutorial-7a9e1.firebaseapp.com",
195
  projectId: "login-tutorial-7a9e1",
196
  storageBucket: "login-tutorial-7a9e1.firebasestorage.app",
197
  messagingSenderId: "491093197824",
198
- appId: "1:491093197824:web:9f866..."
199
  };
200
-
 
201
  const app = initializeApp(firebaseConfig);
202
  const auth = getAuth(app);
203
  const db = getFirestore(app);
204
-
 
 
 
 
 
 
205
  let currentUser = null;
206
-
 
207
  onAuthStateChanged(auth, async (user) => {
 
 
208
  if (user) {
209
  currentUser = user;
210
  await loadUserProfile();
 
 
 
 
 
211
  } else {
212
- window.location.href = 'login.html';
 
 
 
 
213
  }
214
  });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
215
 
216
-
 
217
  async function loadUserProfile() {
218
  try {
219
- const userDoc = await getDoc(doc(db, 'users', currentUser.uid));
220
  if (userDoc.exists()) {
221
  const userData = userDoc.data();
222
- document.getElementById("userName").textContent = userData.name || "Name not set";
223
- document.getElementById("userDOB").textContent = userData.dob || "DOB not set";
 
 
224
  localStorage.setItem("userName", userData.name || "");
225
  localStorage.setItem("userDOB", userData.dob || "");
226
  }
227
  } catch (error) {
228
  console.error("Error loading user profile:", error);
229
  }
230
- }
231
-
 
232
  window.saveProfile = async (name, dob) => {
233
  try {
234
- await updateDoc(doc(db, 'users', currentUser.uid), {
235
  name: name,
236
- dob: dob
237
  });
238
  localStorage.setItem("userName", name);
239
  localStorage.setItem("userDOB", dob);
@@ -243,19 +346,19 @@
243
  return false;
244
  }
245
  };
246
-
247
-
248
  window.logout = async () => {
249
  try {
250
  await signOut(auth);
251
  localStorage.clear();
252
- window.location.href = 'login.html';
253
  } catch (error) {
254
  console.error("Error signing out:", error);
255
  }
256
  };
257
-
258
-
259
  function loadProgressData() {
260
  return JSON.parse(localStorage.getItem("progressData") || "[]");
261
  }
@@ -265,9 +368,9 @@
265
  function resetProgressData() {
266
  localStorage.removeItem("progressData");
267
  }
268
-
 
269
  document.addEventListener("DOMContentLoaded", () => {
270
-
271
  const profileView = document.getElementById("profileViewSection");
272
  const profileEdit = document.getElementById("profileEditSection");
273
  const editBtn = document.getElementById("editProfileBtn");
@@ -275,52 +378,52 @@
275
  const cancelBtn = document.getElementById("cancelProfileBtn");
276
  const inputName = document.getElementById("inputName");
277
  const inputDOB = document.getElementById("inputDOB");
278
- // const inputFix = document.getElementById("inputFix");
279
- // const inputGoals = document.getElementById("inputGoals");
280
-
281
  editBtn.addEventListener("click", () => {
282
  inputName.value = document.getElementById("userName").textContent;
283
  inputDOB.value = document.getElementById("userDOB").textContent;
284
  profileView.classList.add("hidden");
285
  profileEdit.classList.remove("hidden");
286
  });
287
-
 
288
  saveBtn.addEventListener("click", async () => {
289
  const nameVal = inputName.value.trim();
290
  const dobVal = inputDOB.value;
291
-
292
  const success = await window.saveProfile(nameVal, dobVal);
293
-
294
  if (success) {
295
- document.getElementById("userName").textContent = nameVal || "Name not set";
296
- document.getElementById("userDOB").textContent = dobVal || "DOB not set";
 
 
297
  profileEdit.classList.add("hidden");
298
  profileView.classList.remove("hidden");
299
  } else {
300
  alert("Error saving profile. Please try again.");
301
  }
302
  });
 
 
303
  cancelBtn.addEventListener("click", () => {
304
  profileEdit.classList.add("hidden");
305
  profileView.classList.remove("hidden");
306
  });
307
-
 
308
  const chartSection = document.getElementById("chartSection");
309
  const welcomeMessage = document.getElementById("welcomeMessage");
310
  const isNewUser = localStorage.getItem("isNewUser") === "true";
311
-
312
  if (isNewUser) {
313
  welcomeMessage.classList.remove("hidden");
314
  chartSection.classList.add("hidden");
315
  }
316
-
317
- //chart logic(line graph)
318
  const stored = loadProgressData();
319
  const labels = stored.map((e) => e.date);
320
- const dataPoints = [
321
- {x:50, y:7},
322
- {x:70, y:30},
323
- ];
324
  const ctx = document.getElementById("progressChart").getContext("2d");
325
  const progressChart = new Chart(ctx, {
326
  type: "line",
@@ -329,7 +432,7 @@
329
  datasets: [
330
  {
331
  label: "Health Score",
332
- data: dataPoints,
333
  borderColor: "#6B9080",
334
  fill: true,
335
  tension: 0.4,
@@ -340,45 +443,57 @@
340
  scales: { y: { beginAtZero: true, max: 100 } },
341
  },
342
  });
343
-
 
344
  document.getElementById("addEntryBtn").addEventListener("click", () => {
345
  const date = document.getElementById("entryDate").value;
346
- const score = parseInt(
347
- document.getElementById("entryScore").value,
348
- 10
349
- );
350
  if (!date || isNaN(score)) {
351
  alert("Please select a date and enter a valid score.");
352
  return;
353
  }
354
-
355
  stored.push({ date, score });
356
  saveProgressData(stored);
357
  progressChart.data.labels.push(date);
358
  progressChart.data.datasets[0].data.push(score);
359
  progressChart.update();
360
-
361
  document.getElementById("entryDate").value = "";
362
  document.getElementById("entryScore").value = "";
 
363
  if (isNewUser) {
364
  localStorage.setItem("isNewUser", "false");
365
  welcomeMessage.classList.add("hidden");
366
  chartSection.classList.remove("hidden");
367
  }
368
  });
369
-
370
- // Reset Button
371
- document
372
- .getElementById("resetChartBtn")
373
- .addEventListener("click", () => {
374
- if (!confirm("Are you sure you want to clear all progress data?"))
375
- return;
376
- resetProgressData();
377
- progressChart.data.labels = [];
378
- progressChart.data.datasets[0].data = [];
379
- progressChart.update();
380
- });
381
  });
 
 
 
 
 
 
 
 
 
 
 
 
 
 
382
  </script>
 
383
  </body>
384
- </html>
 
6
  <title>Profile - CTRL + ALT + HEAL</title>
7
  <script src="https://cdn.tailwindcss.com"></script>
8
  <script src="https://cdn.jsdelivr.net/npm/chart.js"></script>
9
+ <link rel="stylesheet" href="style.css" />
10
  </head>
11
+ <body class="bg-[#F7F8F9] min-h-screen">
12
+ <!-- NAVBAR -->
13
+ <nav
14
+ class="fixed top-0 left-0 w-full z-50 backdrop-blur-md bg-white/20 border-b border-white/30 shadow-md"
15
+ >
16
+ <div class="flex justify-between items-center w-full px-6 py-4">
17
+ <!-- Logo -->
18
+ <a
19
+ href="index.html"
20
+ class="text-2xl font-bold text-black hover:text-[var(--tropical-indigo)] transition"
21
  >
22
+ CTRL + ALT + HEAL
23
+ </a>
24
+
25
+ <ul class="hidden md:flex space-x-6 font-medium text-gray-800">
26
+ <li><a href="index.html" class="nav-link">Home</a></li>
27
+ <li><a href="analyzer.html" class="nav-link">Analyzer</a></li>
28
+ <li><a href="past_data.html" class="nav-link">Past Reports</a></li>
29
+ <li><a href="profile.html" class="nav-link">Profile</a></li>
30
+ <li id="authNavItem"><a href="login.html" class="nav-link">Login</a></li>
31
  </ul>
32
+
33
+ <!-- Hamburger Menu -->
34
+ <button
35
+ id="hamburger"
36
+ class="md:hidden text-[var(--latte-cream)] text-2xl"
37
+ >
38
+
39
+ </button>
40
  </div>
41
+ <!-- Changes added for change marker for style change-->
42
+ <!-- Mobile Menu -->
43
+ <ul
44
+ id="mobile-menu"
45
+ class="hidden flex-col space-y-4 bg-white/30 backdrop-blur-lg border border-white/20 rounded-xl shadow-lg mt-2 p-4 mx-6 md:hidden"
46
+ >
47
+ <li>
48
+ <a
49
+ href="index.html"
50
+ class="block text-gray-800 hover:text-[var(--tropical-indigo)]"
51
+ >Home</a
52
+ >
53
+ </li>
54
+ <li>
55
+ <a
56
+ href="analyzer.html"
57
+ class="block text-gray-800 hover:text-[var(--tropical-indigo)]"
58
+ >Analyzer</a
59
+ >
60
+ </li>
61
+ <li>
62
+ <a
63
+ href="profile.html"
64
+ class="block text-gray-800 hover:text-[var(--tropical-indigo)]"
65
+ >Profile</a
66
+ >
67
+ </li>
68
+ <li>
69
+ <a
70
+ href="login.html"
71
+ class="block text-gray-800 hover:text-[var(--tropical-indigo)]"
72
+ >Login</a
73
+ >
74
+ </li>
75
+ <li>
76
+ <a
77
+ href="about.html"
78
+ class="block text-gray-800 hover:text-[var(--tropical-indigo)]"
79
+ >About</a
80
+ >
81
+ </li>
82
+
83
+ >
84
+ </li>
85
+ </ul>
86
  </nav>
87
 
88
+ <script>
89
+ const hamburger = document.getElementById("hamburger");
90
+ const mobileMenu = document.getElementById("mobile-menu");
91
+ hamburger.addEventListener("click", () => {
92
+ mobileMenu.classList.toggle("hidden");
93
+ });
94
+ // Underline the active page only
95
+ const currentPath = window.location.pathname.split("/").pop();
96
+ document.querySelectorAll(".nav-link").forEach((link) => {
97
+ if (link.getAttribute("href") === currentPath) {
98
+ link.classList.add("active-page"); // we'll style this in CSS
99
+ }
100
+ });
101
+ document.querySelectorAll("#mobile-menu a").forEach((link) => {
102
+ if (link.getAttribute("href") === currentPath) {
103
+ link.classList.add("active-page");
104
+ }
105
+ });
106
+ </script>
107
+
108
+ <div class="container mx-auto px-6 pt-[var(--navbar-height)]">
109
  <!-- VIEW MODE -->
110
  <div id="profileViewSection">
111
  <div class="flex items-start space-x-6 mb-10">
112
  <!-- Avatar & Edit Button -->
113
  <div class="flex flex-col items-center">
114
  <div class="w-32 h-32 bg-gray-300 rounded-full"></div>
115
+ <button id="editProfileBtn" class="mt-2 px-4 py-2 rounded">
 
 
 
116
  Edit Profile
117
  </button>
118
  <a href="analyzer.html"
119
+ ><button id="analyzerBtn" class="mt-2 px-4 py-2 rounded">
 
 
120
  Go To Analyzer
121
+ </button></a
122
+ >
123
  </div>
124
 
 
 
125
  <!-- User Info -->
126
  <div>
127
+ <h1 class="text-3xl font-semibold mb-4">Your Profile</h1>
128
+ <p class="mb-2">
 
 
129
  Name: <span id="userName" class="font-medium">Loading...</span>
130
  </p>
131
+ <p class="mb-2">
132
+ DOB: <span id="userDOB" class="font-medium">Loading...</span>
133
  </p>
 
 
 
 
 
 
 
134
  </div>
135
  </div>
136
  </div>
 
138
  <!-- EDIT MODE -->
139
  <div id="profileEditSection" class="hidden mb-10">
140
  <div class="flex flex-col sm:flex-row items-start space-x-6">
 
141
  <div class="flex flex-col items-center mb-4 sm:mb-0">
142
  <div class="w-32 h-32 bg-gray-300 rounded-full"></div>
143
  </div>
 
144
  <div class="flex-1">
145
+ <h1 class="text-3xl font-semibold mb-4">Edit Profile</h1>
 
 
146
  <div class="space-y-4">
147
  <div>
148
+ <label for="inputName" class="block text-sm font-medium"
 
 
149
  >Name</label
150
  >
151
  <input
152
  type="text"
153
  id="inputName"
154
+ class="w-full border rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
155
  />
156
  </div>
157
  <div>
158
+ <label for="inputDOB" class="block text-sm font-medium"
 
 
159
  >Date of Birth</label
160
  >
161
  <input
162
  type="date"
163
  id="inputDOB"
164
+ class="w-full border rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
165
  />
166
  </div>
 
167
  </div>
168
  <div class="flex space-x-2 mt-4">
169
+ <button id="saveProfileBtn" class="px-4 py-2 rounded">
 
 
 
170
  Save
171
  </button>
172
+ <button id="cancelProfileBtn" class="px-4 py-2 rounded">
 
 
 
173
  Cancel
174
  </button>
175
  </div>
 
177
  </div>
178
  </div>
179
 
 
180
  <!-- Chart Section -->
181
  <div class="mt-10" id="chartSection">
 
182
  <div class="bg-white border border-gray-200 rounded-lg p-6 mb-6">
183
+ <h2 class="text-xl font-semibold mb-4">Health Progress</h2>
 
 
 
 
184
  <div
185
  class="flex flex-col sm:flex-row sm:items-center sm:justify-between gap-4 mb-6"
186
  >
 
187
  <div class="flex flex-1 gap-2">
188
  <input
189
  type="date"
190
  id="entryDate"
191
+ class="flex-1 border rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
192
  />
193
  <input
194
  type="number"
 
196
  min="0"
197
  max="100"
198
  placeholder="Score"
199
+ class="w-24 border rounded px-3 py-2 focus:ring-2 focus:ring-[#6B9080] focus:outline-none"
200
  />
201
  </div>
 
202
  <div class="flex gap-2">
203
+ <button id="addEntryBtn" class="px-4 py-2 rounded">
 
 
 
204
  Add Entry
205
  </button>
206
+ <button id="resetChartBtn" class="px-4 py-2 rounded">
 
 
 
207
  Reset Chart
208
  </button>
209
  </div>
210
  </div>
 
 
211
  <div class="overflow-x-auto">
212
  <canvas id="progressChart" class="w-full h-64"></canvas>
213
  </div>
 
216
  </div>
217
 
218
  <script type="module">
219
+ import { initializeApp } from "https://www.gstatic.com/firebasejs/9.22.0/firebase-app.js";
220
+ import {
221
+ getAuth,
222
+ onAuthStateChanged,
223
+ signOut,
224
+ } from "https://www.gstatic.com/firebasejs/9.22.0/firebase-auth.js";
225
+ import {
226
+ getFirestore,
227
+ doc,
228
+ getDoc,
229
+ updateDoc,
230
+ collection,
231
+ addDoc,
232
+ serverTimestamp,
233
+ } from "https://www.gstatic.com/firebasejs/9.22.0/firebase-firestore.js";
234
+
235
+ // 🔥 Firebase config
236
  const firebaseConfig = {
237
  apiKey: "AIzaSyAPhM_Ee7cLzyKHs5zyFy8g5ZOk9-pubRI",
238
  authDomain: "login-tutorial-7a9e1.firebaseapp.com",
239
  projectId: "login-tutorial-7a9e1",
240
  storageBucket: "login-tutorial-7a9e1.firebasestorage.app",
241
  messagingSenderId: "491093197824",
242
+ appId: "1:491093197824:web:9f866...",
243
  };
244
+
245
+ // 🔧 Init
246
  const app = initializeApp(firebaseConfig);
247
  const auth = getAuth(app);
248
  const db = getFirestore(app);
249
+
250
+ // Expose Firestore helpers if you need them elsewhere
251
+ window.firebaseAuth = auth;
252
+ window.onAuthStateChanged = onAuthStateChanged;
253
+ window.firestoreDb = db;
254
+ window.firestoreHelpers = { collection, doc, addDoc, serverTimestamp };
255
+
256
  let currentUser = null;
257
+
258
+ // ✅ Auth state check
259
  onAuthStateChanged(auth, async (user) => {
260
+ const authNavItem = document.getElementById("authNavItem");
261
+
262
  if (user) {
263
  currentUser = user;
264
  await loadUserProfile();
265
+
266
+ if (authNavItem) {
267
+ authNavItem.innerHTML =
268
+ '<button onclick="logout()" class="hover:text-[#6B9080] text-red-600">Logout</button>';
269
+ }
270
  } else {
271
+ if (authNavItem) {
272
+ authNavItem.innerHTML =
273
+ '<a href="login.html" class="hover:text-[#6B9080]">Login</a>';
274
+ }
275
+ window.location.href = "login.html";
276
  }
277
  });
278
+ // ✅ Hide Home button when logged in
279
+ const homeNavDesktop = document.querySelector('ul.md\\:flex li a[href="index.html"]')
280
+ ?.parentElement; // Desktop <li>
281
+ const homeNavMobile = document.querySelector('#mobile-menu a[href="index.html"]')
282
+ ?.parentElement; // Mobile <li>
283
+
284
+ onAuthStateChanged(auth, async (user) => {
285
+ const authNavItem = document.getElementById("authNavItem");
286
+
287
+ if (user) {
288
+ currentUser = user;
289
+ await loadUserProfile();
290
+
291
+ // Swap login with logout
292
+ if (authNavItem) {
293
+ authNavItem.innerHTML =
294
+ '<button onclick="logout()" class="hover:text-[#6B9080] text-red-600">Logout</button>';
295
+ }
296
+
297
+ // Hide Home button
298
+ if (homeNavDesktop) homeNavDesktop.style.display = "none";
299
+ if (homeNavMobile) homeNavMobile.style.display = "none";
300
+
301
+ } else {
302
+ if (authNavItem) {
303
+ authNavItem.innerHTML =
304
+ '<a href="login.html" class="hover:text-[#6B9080]">Login</a>';
305
+ }
306
+
307
+ // Show Home button again
308
+ if (homeNavDesktop) homeNavDesktop.style.display = "";
309
+ if (homeNavMobile) homeNavMobile.style.display = "";
310
+
311
+ window.location.href = "login.html";
312
+ }
313
+ });
314
 
315
+
316
+ // 📄 Load user profile from Firestore
317
  async function loadUserProfile() {
318
  try {
319
+ const userDoc = await getDoc(doc(db, "users", currentUser.uid));
320
  if (userDoc.exists()) {
321
  const userData = userDoc.data();
322
+ document.getElementById("userName").textContent =
323
+ userData.name || "Name not set";
324
+ document.getElementById("userDOB").textContent =
325
+ userData.dob || "DOB not set";
326
  localStorage.setItem("userName", userData.name || "");
327
  localStorage.setItem("userDOB", userData.dob || "");
328
  }
329
  } catch (error) {
330
  console.error("Error loading user profile:", error);
331
  }
332
+ }
333
+
334
+ // 💾 Save profile to Firestore
335
  window.saveProfile = async (name, dob) => {
336
  try {
337
+ await updateDoc(doc(db, "users", currentUser.uid), {
338
  name: name,
339
+ dob: dob,
340
  });
341
  localStorage.setItem("userName", name);
342
  localStorage.setItem("userDOB", dob);
 
346
  return false;
347
  }
348
  };
349
+
350
+ // 🚪 Logout
351
  window.logout = async () => {
352
  try {
353
  await signOut(auth);
354
  localStorage.clear();
355
+ window.location.href = "login.html";
356
  } catch (error) {
357
  console.error("Error signing out:", error);
358
  }
359
  };
360
+
361
+ // 📊 LocalStorage for progress data
362
  function loadProgressData() {
363
  return JSON.parse(localStorage.getItem("progressData") || "[]");
364
  }
 
368
  function resetProgressData() {
369
  localStorage.removeItem("progressData");
370
  }
371
+
372
+ // 🖼️ DOM Content Loaded logic
373
  document.addEventListener("DOMContentLoaded", () => {
 
374
  const profileView = document.getElementById("profileViewSection");
375
  const profileEdit = document.getElementById("profileEditSection");
376
  const editBtn = document.getElementById("editProfileBtn");
 
378
  const cancelBtn = document.getElementById("cancelProfileBtn");
379
  const inputName = document.getElementById("inputName");
380
  const inputDOB = document.getElementById("inputDOB");
381
+
382
+ // Toggle to edit mode
 
383
  editBtn.addEventListener("click", () => {
384
  inputName.value = document.getElementById("userName").textContent;
385
  inputDOB.value = document.getElementById("userDOB").textContent;
386
  profileView.classList.add("hidden");
387
  profileEdit.classList.remove("hidden");
388
  });
389
+
390
+ // Save profile
391
  saveBtn.addEventListener("click", async () => {
392
  const nameVal = inputName.value.trim();
393
  const dobVal = inputDOB.value;
394
+
395
  const success = await window.saveProfile(nameVal, dobVal);
396
+
397
  if (success) {
398
+ document.getElementById("userName").textContent =
399
+ nameVal || "Name not set";
400
+ document.getElementById("userDOB").textContent =
401
+ dobVal || "DOB not set";
402
  profileEdit.classList.add("hidden");
403
  profileView.classList.remove("hidden");
404
  } else {
405
  alert("Error saving profile. Please try again.");
406
  }
407
  });
408
+
409
+ // Cancel editing
410
  cancelBtn.addEventListener("click", () => {
411
  profileEdit.classList.add("hidden");
412
  profileView.classList.remove("hidden");
413
  });
414
+
415
+ // Chart setup
416
  const chartSection = document.getElementById("chartSection");
417
  const welcomeMessage = document.getElementById("welcomeMessage");
418
  const isNewUser = localStorage.getItem("isNewUser") === "true";
419
+
420
  if (isNewUser) {
421
  welcomeMessage.classList.remove("hidden");
422
  chartSection.classList.add("hidden");
423
  }
424
+
 
425
  const stored = loadProgressData();
426
  const labels = stored.map((e) => e.date);
 
 
 
 
427
  const ctx = document.getElementById("progressChart").getContext("2d");
428
  const progressChart = new Chart(ctx, {
429
  type: "line",
 
432
  datasets: [
433
  {
434
  label: "Health Score",
435
+ data: stored.map((e) => e.score),
436
  borderColor: "#6B9080",
437
  fill: true,
438
  tension: 0.4,
 
443
  scales: { y: { beginAtZero: true, max: 100 } },
444
  },
445
  });
446
+
447
+ // Add Entry
448
  document.getElementById("addEntryBtn").addEventListener("click", () => {
449
  const date = document.getElementById("entryDate").value;
450
+ const score = parseInt(document.getElementById("entryScore").value, 10);
451
+
 
 
452
  if (!date || isNaN(score)) {
453
  alert("Please select a date and enter a valid score.");
454
  return;
455
  }
456
+
457
  stored.push({ date, score });
458
  saveProgressData(stored);
459
  progressChart.data.labels.push(date);
460
  progressChart.data.datasets[0].data.push(score);
461
  progressChart.update();
462
+
463
  document.getElementById("entryDate").value = "";
464
  document.getElementById("entryScore").value = "";
465
+
466
  if (isNewUser) {
467
  localStorage.setItem("isNewUser", "false");
468
  welcomeMessage.classList.add("hidden");
469
  chartSection.classList.remove("hidden");
470
  }
471
  });
472
+
473
+ // Reset Chart
474
+ document.getElementById("resetChartBtn").addEventListener("click", () => {
475
+ if (!confirm("Are you sure you want to clear all progress data?")) return;
476
+ resetProgressData();
477
+ progressChart.data.labels = [];
478
+ progressChart.data.datasets[0].data = [];
479
+ progressChart.update();
480
+ });
 
 
 
481
  });
482
+
483
+ // 🪄 Navbar padding adjust
484
+ function updateNavbarPadding() {
485
+ const nav = document.querySelector("nav");
486
+ if (nav) {
487
+ const navHeight = nav.offsetHeight;
488
+ document.documentElement.style.setProperty(
489
+ "--navbar-height",
490
+ `${navHeight}px`
491
+ );
492
+ }
493
+ }
494
+ updateNavbarPadding();
495
+ window.addEventListener("resize", updateNavbarPadding);
496
  </script>
497
+
498
  </body>
499
+ </html>
web/style.css ADDED
@@ -0,0 +1,246 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ :root {
2
+ --tropical-indigo: rgb(120, 187, 242);
3
+ --latte-cream: #ffffff;
4
+ --wisteria: #c5dcff;
5
+ --navbar-height: 0px; /* dynamic padding */
6
+ }
7
+
8
+ body {
9
+ padding-top: var(--navbar-height);
10
+ transition: padding-top 0.2s ease;
11
+ font-family: "Rubik", sans-serif;
12
+ }
13
+
14
+ /* ---------- NAVBAR area---------- */
15
+ nav {
16
+ backdrop-filter: blur(12px);
17
+ background-color: rgba(255, 255, 255, 0.2);
18
+ border-bottom: 1px solid rgba(255, 255, 255, 0.3);
19
+ box-shadow: 0 2px 6px rgba(0, 0, 0, 0.05);
20
+ }
21
+
22
+ /* Logo */
23
+ nav .logo {
24
+ color: #333;
25
+ font-weight: bold;
26
+ transition: color 0.3s ease;
27
+ }
28
+ nav .logo:hover {
29
+ color: var(--tropical-indigo);
30
+ }
31
+
32
+ /* Desktop links and buttons */
33
+ nav a.nav-link,
34
+ nav button.nav-link {
35
+ color: #333;
36
+ transition: color 0.3s ease;
37
+ }
38
+
39
+ /* Hamburger */
40
+ #hamburger {
41
+ color: #333;
42
+ transition: color 0.3s ease;
43
+ }
44
+ #hamburger:hover {
45
+ color: var(--tropical-indigo);
46
+ }
47
+
48
+ /* Mobile Menu */
49
+ #mobile-menu {
50
+ backdrop-filter: blur(12px);
51
+ background-color: rgba(255, 255, 255, 0.3);
52
+ border: 1px solid rgba(255, 255, 255, 0.2);
53
+ border-radius: 1rem;
54
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.08);
55
+ }
56
+ #mobile-menu a,
57
+ #mobile-menu button {
58
+
59
+ color: #333;
60
+ transition: color 0.3s ease;
61
+ }
62
+
63
+
64
+ /* ---------- BUTTONS ---------- */
65
+ #editProfileBtn,
66
+ #saveProfileBtn,
67
+ #cancelProfileBtn,
68
+ #addEntryBtn,
69
+ #resetChartBtn,
70
+ #analyzerBtn {
71
+ background-color: var(--tropical-indigo);
72
+ color: white;
73
+ transition: background-color 0.3s ease;
74
+ }
75
+ #editProfileBtn:hover,
76
+ #saveProfileBtn:hover,
77
+ #addEntryBtn:hover,
78
+ #analyzerBtn:hover {
79
+ background-color: #5ba5dd;
80
+ }
81
+ #resetChartBtn:hover {
82
+ background-color: #e63946;
83
+ }
84
+
85
+ /* ---------- INPUTS ---------- */
86
+ input,
87
+ textarea {
88
+ border: 1px solid var(--wisteria);
89
+ background-color: #fafbfc;
90
+ }
91
+ input:focus,
92
+ textarea:focus {
93
+ outline: none;
94
+ border-color: var(--tropical-indigo);
95
+ box-shadow: 0 0 0 2px rgba(120, 187, 242, 0.3);
96
+ }
97
+
98
+ /* HEADINGS */
99
+ h1,
100
+ h2,
101
+ h3,
102
+ h4 {
103
+ color: var(--tropical-indigo);
104
+ }
105
+
106
+ /* Chart Card */
107
+ #chartSection > div {
108
+ background-color: var(--latte-cream);
109
+ border: 1px solid var(--wisteria);
110
+ border-radius: 1rem;
111
+ padding: 1.5rem;
112
+ }
113
+ .rec-card {
114
+ background-color: var(--latte-cream);
115
+ border: 1px solid var(--wisteria);
116
+ border-radius: 1rem;
117
+ padding: 1.25rem;
118
+ margin-bottom: 1.5rem;
119
+ box-shadow: 0 2px 8px rgba(0, 0, 0, 0.08);
120
+ transition: all 0.3s ease;
121
+ }
122
+ .rec-card:hover {
123
+ transform: translateY(-3px);
124
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.12);
125
+ }
126
+ .rec-title {
127
+ font-size: 1.125rem;
128
+ font-weight: 700;
129
+ color: var(--tropical-indigo);
130
+ margin-bottom: 0.5rem;
131
+ }
132
+ .rec-badge {
133
+ font-size: 0.75rem;
134
+ font-weight: 600;
135
+ padding: 0.25rem 0.75rem;
136
+ border-radius: 9999px;
137
+ }
138
+ .badge-high {
139
+ background-color: #fee2e2;
140
+ color: #b91c1c;
141
+ }
142
+ .badge-medium {
143
+ background-color: #fef3c7;
144
+ color: #92400e;
145
+ }
146
+ .badge-low {
147
+ background-color: #d1fae5;
148
+ color: #065f46;
149
+ }
150
+ .rec-content {
151
+ list-style-type: disc;
152
+ margin-left: 1.25rem;
153
+ font-size: 0.875rem;
154
+ color: #374151;
155
+ }
156
+ .rec-link {
157
+ color: var(--tropical-indigo);
158
+ text-decoration: underline;
159
+ }
160
+ .rec-link:hover {
161
+ color: #4b7bbd;
162
+ }
163
+ .btn-primary {
164
+ background-color: var(--tropical-indigo);
165
+ color: white;
166
+ transition: background-color 0.3s ease;
167
+ }
168
+ .btn-primary:hover {
169
+ background-color: #5ba5dd;
170
+ }
171
+ input,
172
+ textarea {
173
+ border: 1px solid var(--wisteria);
174
+ background-color: #fafbfc;
175
+ }
176
+ input:focus,
177
+ textarea:focus {
178
+ outline: none;
179
+ border-color: var(--tropical-indigo);
180
+ box-shadow: 0 0 0 2px rgba(120, 187, 242, 0.3);
181
+ }
182
+ h2,
183
+ h3 {
184
+ color: var(--tropical-indigo);
185
+ }
186
+ #chat-output {
187
+ background-color: #f7f9fc;
188
+ border: 1px solid var(--wisteria);
189
+ }
190
+ .fade-in {
191
+ opacity: 0;
192
+ transform: translateY(30px);
193
+ transition: all 0.8s ease-out;
194
+ }
195
+ .fade-in.show {
196
+ opacity: 1;
197
+ transform: translateY(0);
198
+ }
199
+
200
+ .glass-card {
201
+ background: rgba(162, 160, 160, 0.075);
202
+ backdrop-filter: blur(12px);
203
+ border-radius: 1rem;
204
+ border: 1px solid rgba(255, 255, 255, 0.3);
205
+ padding: 2rem;
206
+ text-align: center;
207
+ transition: transform 0.3s ease, box-shadow 0.3s ease;
208
+ }
209
+ .glass-card:hover {
210
+ transform: translateY(-5px);
211
+ box-shadow: 0 15px 25px rgba(0, 0, 0, 0.2);
212
+ }
213
+
214
+ .nav-link {
215
+ position: relative;
216
+ padding-bottom: 4px;
217
+ transition: color 0.3s;
218
+ }
219
+ .nav-link::after {
220
+ content: "";
221
+ position: absolute;
222
+ width: 0%;
223
+ height: 2px;
224
+ bottom: 0;
225
+ left: 0;
226
+ background-color: black;
227
+ transition: width 0.3s ease;
228
+ }
229
+ .nav-link:hover::after {
230
+ width: 100%;
231
+ }
232
+
233
+ .parallax {
234
+ background-attachment: fixed;
235
+ background-size: cover;
236
+ background-position: center;
237
+ position: relative;
238
+ }
239
+
240
+ /* Typing effect styles */
241
+ #typed-heading,
242
+ #typed-paragraph {
243
+ overflow: hidden;
244
+ white-space: nowrap;
245
+ border-right: 2px solid var(--tropical-indigo);
246
+ }