Ashrafb commited on
Commit
df13995
1 Parent(s): 48cc8ce

Upload static_index (54).html

Browse files
Files changed (1) hide show
  1. static/static_index (54).html +443 -0
static/static_index (54).html ADDED
@@ -0,0 +1,443 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+
2
+ <!DOCTYPE html>
3
+ <html lang="en" dir="ltr">
4
+ <head>
5
+ <meta charset="utf-8">
6
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
7
+ <!-- Google Fonts Link For Icons -->
8
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Material+Symbols+Rounded:opsz,wght,FILL,GRAD@20..48,100..700,0..1,-50..200" />
9
+ <style>
10
+ /* Import Google font - Poppins */
11
+ @import url('https://fonts.googleapis.com/css2?family=Poppins:wght@400;500;600&display=swap');
12
+ * {
13
+ margin: 0;
14
+ padding: 0;
15
+ box-sizing: border-box;
16
+ font-family: "Poppins", sans-serif;
17
+ }
18
+ :root {
19
+ --text-color: #FFFFFF;
20
+ --icon-color: #ACACBE;
21
+ --icon-hover-bg: #5b5e71;
22
+ --placeholder-color: #dcdcdc;
23
+ --outgoing-chat-bg: #343541;
24
+ --incoming-chat-bg: #444654;
25
+ --outgoing-chat-border: #343541;
26
+ --incoming-chat-border: #444654;
27
+ }
28
+ .light-mode {
29
+ --text-color: #343541;
30
+ --icon-color: #a9a9bc;
31
+ --icon-hover-bg: #f1f1f3;
32
+ --placeholder-color: #6c6c6c;
33
+ --outgoing-chat-bg: #FFFFFF;
34
+ --incoming-chat-bg: #F7F7F8;
35
+ --outgoing-chat-border: #FFFFFF;
36
+ --incoming-chat-border: #D9D9E3;
37
+ }
38
+ body {
39
+ background: var(--outgoing-chat-bg);
40
+ }
41
+ .top-bar {
42
+ background: var(--outgoing-chat-bg);
43
+ border-bottom: 1px solid var(--incoming-chat-border);
44
+ padding: 10px;
45
+ text-align: center;
46
+ color: var(--text-color);
47
+ }
48
+ /* Chats container styling */
49
+ .chat-container {
50
+ overflow-y: auto;
51
+ max-height: 100vh;
52
+ padding-bottom: 150px;
53
+ }
54
+ :where(.chat-container, textarea)::-webkit-scrollbar {
55
+ width: 6px;
56
+ }
57
+ :where(.chat-container, textarea)::-webkit-scrollbar-track {
58
+ background: var(--incoming-chat-bg);
59
+ border-radius: 25px;
60
+ }
61
+ :where(.chat-container, textarea)::-webkit-scrollbar-thumb {
62
+ background: var(--icon-color);
63
+ border-radius: 25px;
64
+ }
65
+ .default-text {
66
+ display: flex;
67
+ align-items: center;
68
+ justify-content: center;
69
+ flex-direction: column;
70
+ height: 70vh;
71
+ padding: 0 10px;
72
+ text-align: center;
73
+ color: var(--text-color);
74
+ }
75
+ .default-text h1 {
76
+ font-size: 3.3rem;
77
+ }
78
+ .default-text p {
79
+ margin-top: 10px;
80
+ font-size: 1.1rem;
81
+ }
82
+ .chat-container .chat {
83
+ padding: 25px 10px;
84
+ display: flex;
85
+ justify-content: center;
86
+ color: var(--text-color);
87
+ position: relative;
88
+ }
89
+ .chat-container .chat.outgoing {
90
+ background: var(--outgoing-chat-bg);
91
+ border: 1px solid var(--outgoing-chat-border);
92
+ }
93
+ .chat-container .chat.incoming {
94
+ background: var(--incoming-chat-bg);
95
+ border: 1px solid var(--incoming-chat-border);
96
+ }
97
+ .chat .chat-content {
98
+ display: flex;
99
+ max-width: 1200px;
100
+ width: 100%;
101
+ align-items: flex-start;
102
+ justify-content: space-between;
103
+ }
104
+ span.material-symbols-rounded {
105
+ user-select: none;
106
+ cursor: pointer;
107
+ }
108
+ .chat .chat-content span {
109
+ cursor: pointer;
110
+ font-size: 1.3rem;
111
+ color: var(--icon-color);
112
+ visibility: hidden;
113
+ }
114
+ .chat:hover .chat-content:not(:has(.typing-animation), :has(.error)) span {
115
+ visibility: visible;
116
+ }
117
+ .chat .chat-details {
118
+ display: flex;
119
+ align-items: center;
120
+ }
121
+ .chat .chat-details img {
122
+ width: 35px;
123
+ height: 35px;
124
+ align-self: flex-start;
125
+ object-fit: cover;
126
+ border-radius: 2px;
127
+ }
128
+ .chat .chat-details p {
129
+ white-space: pre-wrap;
130
+ font-size: 1.05rem;
131
+ padding: 0 50px 0 25px;
132
+ color: var(--text-color);
133
+ word-break: break-word;
134
+ }
135
+ .chat .chat-details p.error {
136
+ color: #e55865;
137
+ }
138
+ .chat .typing-animation {
139
+ padding-left: 25px;
140
+ display: inline-flex;
141
+ }
142
+ .typing-animation .typing-dot {
143
+ height: 7px;
144
+ width: 7px;
145
+ border-radius: 50%;
146
+ margin: 0 3px;
147
+ opacity: 0.7;
148
+ background: var(--text-color);
149
+ animation: animateDots 1.5s var(--delay) ease-in-out infinite;
150
+ }
151
+ .typing-animation .typing-dot:first-child {
152
+ margin-left: 0;
153
+ }
154
+ @keyframes animateDots {
155
+ 0%,
156
+ 44% {
157
+ transform: translateY(0px);
158
+ }
159
+ 28% {
160
+ opacity: 0.4;
161
+ transform: translateY(-6px);
162
+ }
163
+ 44% {
164
+ opacity: 0.2;
165
+ }
166
+ }
167
+ /* Typing container styling */
168
+ .typing-container {
169
+ position: fixed;
170
+ bottom: 0;
171
+ width: 100%;
172
+ display: flex;
173
+ padding: 20px 10px;
174
+ justify-content: center;
175
+ background: var(--outgoing-chat-bg);
176
+ border-top: 1px solid var(--incoming-chat-border);
177
+ }
178
+ .typing-container .typing-content {
179
+ display: flex;
180
+ max-width: 950px;
181
+ width: 100%;
182
+ align-items: flex-end;
183
+ }
184
+ .typing-container .typing-textarea {
185
+ width: 100%;
186
+ display: flex;
187
+ position: relative;
188
+ }
189
+ .typing-textarea textarea {
190
+ resize: none;
191
+ height: 55px;
192
+ width: 100%;
193
+ border: none;
194
+ padding: 15px 45px 15px 20px;
195
+ color: var(--text-color);
196
+ font-size: 1rem;
197
+ border-radius: 4px;
198
+ max-height: 250px;
199
+ overflow-y: auto;
200
+ background: var(--incoming-chat-bg);
201
+ outline: 1px solid var(--incoming-chat-border);
202
+ }
203
+ .typing-textarea textarea::placeholder {
204
+ color: var(--placeholder-color);
205
+ }
206
+ .typing-content span {
207
+ width: 55px;
208
+ height: 55px;
209
+ display: flex;
210
+ border-radius: 4px;
211
+ font-size: 1.35rem;
212
+ align-items: center;
213
+ justify-content: center;
214
+ color: var(--icon-color);
215
+ }
216
+ .typing-textarea span {
217
+ position: absolute;
218
+ right: 0;
219
+ bottom: 0;
220
+ visibility: hidden;
221
+ }
222
+ .typing-textarea textarea:valid ~ span {
223
+ visibility: visible;
224
+ }
225
+ .typing-controls {
226
+ display: flex;
227
+ }
228
+ .typing-controls span {
229
+ margin-left: 7px;
230
+ font-size: 1.4rem;
231
+ background: var(--incoming-chat-bg);
232
+ outline: 1px solid var(--incoming-chat-border);
233
+ }
234
+ .typing-controls span:hover {
235
+ background: var(--icon-hover-bg);
236
+ }
237
+ /* Reponsive Media Query */
238
+ @media screen and (max-width: 600px) {
239
+ .default-text h1 {
240
+ font-size: 2.3rem;
241
+ }
242
+ :where(.default-text p, textarea, .chat p) {
243
+ font-size: 0.95rem!important;
244
+ }
245
+ .chat-container .chat {
246
+ padding: 20px 10px;
247
+ }
248
+ .chat-container .chat img {
249
+ height: 32px;
250
+ width: 32px;
251
+ }
252
+ .chat-container .chat p {
253
+ padding: 0 20px;
254
+ }
255
+ .chat .chat-content:not(:has(.typing-animation), :has(.error)) span {
256
+ visibility: visible;
257
+ }
258
+ .typing-container {
259
+ padding: 15px 10px;
260
+ }
261
+ .typing-container .typing-content {
262
+ max-width: 100%;
263
+ }
264
+ .typing-controls span {
265
+ margin-left: 5px;
266
+ font-size: 1.2rem;
267
+ }
268
+ .typing-textarea textarea {
269
+ padding: 14px 45px 14px 15px;
270
+ font-size: 0.95rem;
271
+ }
272
+ }
273
+ </style>
274
+ </head>
275
+ <body>
276
+ <div class="top-bar">
277
+ <img src="img/chatbot.jpg">
278
+ <span>Hello there! <br> How can I help you today.</span>
279
+ </div>
280
+ <div class="chat-container">
281
+ <div class="default-text">
282
+ <h1>Welcome</h1>
283
+ <p>Start a conversation with the AI assistant.</p>
284
+ </div>
285
+ </div>
286
+ <div class="typing-container">
287
+ <div class="typing-content">
288
+ <div class="typing-textarea">
289
+ <textarea spellcheck="false" placeholder="Type your message.."></textarea>
290
+ <span class="material-symbols-rounded">send</span>
291
+ </div>
292
+ <div class="typing-controls">
293
+ <span class="material-symbols-rounded">dark_mode</span>
294
+ </div>
295
+ </div>
296
+ </div>
297
+ <script>
298
+ const textarea = document.querySelector("textarea"),
299
+ chatContainer = document.querySelector(".chat-container"),
300
+ sendChatBtn = document.querySelector("span.material-symbols-rounded"),
301
+ toggleIcon = document.querySelector(".typing-controls span"),
302
+ defaultText = document.querySelector(".default-text");
303
+
304
+ let userMessage = null;
305
+
306
+ toggleIcon.onclick = () => {
307
+ document.body.classList.toggle("light-mode");
308
+ };
309
+
310
+ const createTypingAnimation = () => {
311
+ const html = `
312
+ <div class="chat-content">
313
+ <div class="chat-details">
314
+ <img src="img/chatbot.jpg" alt="">
315
+ <div class="typing-animation">
316
+ <div class="typing-dot" style="--delay: 0s"></div>
317
+ <div class="typing-dot" style="--delay: 0.15s"></div>
318
+ <div class="typing-dot" style="--delay: 0.3s"></div>
319
+ </div>
320
+ </div>
321
+ </div>`;
322
+ const incomingChat = document.createElement("div");
323
+ incomingChat.classList.add("chat", "incoming");
324
+ incomingChat.innerHTML = html;
325
+ return incomingChat;
326
+ };
327
+
328
+ const generateResponse = (chatElement) => {
329
+ const API_URL = "/generate/";
330
+
331
+ const requestOptions = {
332
+ method: "POST",
333
+ headers: {
334
+ "Content-Type": "application/x-www-form-urlencoded"
335
+ },
336
+ body: new URLSearchParams({
337
+ prompt: userMessage,
338
+ history: "[]",
339
+ temperature: "0.9",
340
+ max_new_tokens: "512",
341
+ top_p: "0.95",
342
+ repetition_penalty: "1.0"
343
+ })
344
+ };
345
+
346
+ fetch(API_URL, requestOptions).then(res => res.json()).then(data => {
347
+ chatElement.querySelector(".typing-animation").remove();
348
+ const pElement = document.createElement("p");
349
+ pElement.textContent = data.response;
350
+ chatElement.querySelector(".chat-details").appendChild(pElement);
351
+
352
+ // Add regenerate icon
353
+ const regenerateIcon = document.createElement("span");
354
+ regenerateIcon.classList.add("material-symbols-rounded");
355
+ regenerateIcon.textContent = "refresh";
356
+ regenerateIcon.addEventListener("click", () => regenerateResponse(chatElement, userMessage));
357
+ chatElement.querySelector(".chat-content").appendChild(regenerateIcon);
358
+
359
+ }).catch(() => {
360
+ chatElement.querySelector(".typing-animation").remove();
361
+ const pElement = document.createElement("p");
362
+ pElement.classList.add("error");
363
+ pElement.textContent = "Oops! Something went wrong. Please try again.";
364
+ chatElement.querySelector(".chat-details").appendChild(pElement);
365
+ }).finally(() => chatContainer.scrollTo(0, chatContainer.scrollHeight));
366
+ };
367
+
368
+ const regenerateResponse = (chatElement, message) => {
369
+ const typingAnimation = createTypingAnimation();
370
+ chatElement.replaceWith(typingAnimation);
371
+ generateResponse(typingAnimation);
372
+ };
373
+
374
+ const copyMessage = (element) => {
375
+ navigator.clipboard.writeText(element.innerText);
376
+ };
377
+
378
+ const createChatElement = (message, className) => {
379
+ const chatElement = document.createElement("div");
380
+ chatElement.classList.add("chat", className);
381
+
382
+ const html = `
383
+ <div class="chat-content">
384
+ <div class="chat-details">
385
+ <img src="${className === "outgoing" ? "img/user.jpg" : "img/chatbot.jpg"}" alt="">
386
+ <p>${message}</p>
387
+ </div>
388
+ <span class="material-symbols-rounded">content_copy</span>
389
+ ${className === "outgoing" ? '<span class="material-symbols-rounded">edit</span>' : ''}
390
+ </div>`;
391
+ chatElement.innerHTML = html;
392
+
393
+ if (className === "outgoing") {
394
+ const editIcon = chatElement.querySelector(".material-symbols-rounded:nth-child(3)");
395
+ editIcon.addEventListener("click", () => {
396
+ textarea.value = message;
397
+ chatElement.remove();
398
+ textarea.focus();
399
+ });
400
+ }
401
+
402
+ const copyIcon = chatElement.querySelector(".material-symbols-rounded:nth-child(2)");
403
+ copyIcon.addEventListener("click", () => copyMessage(chatElement.querySelector("p")));
404
+
405
+ return chatElement;
406
+ };
407
+
408
+ const handleChat = () => {
409
+ userMessage = textarea.value.trim();
410
+ if (!userMessage) return;
411
+
412
+ textarea.value = "";
413
+ textarea.style.height = `${textarea.scrollHeight}px`;
414
+
415
+ if (!chatContainer.querySelector(".chat")) defaultText.style.display = "none";
416
+
417
+ chatContainer.appendChild(createChatElement(userMessage, "outgoing"));
418
+ chatContainer.scrollTo(0, chatContainer.scrollHeight);
419
+
420
+ const incomingChat = createTypingAnimation();
421
+ chatContainer.appendChild(incomingChat);
422
+ chatContainer.scrollTo(0, chatContainer.scrollHeight);
423
+
424
+ generateResponse(incomingChat);
425
+ };
426
+
427
+ textarea.addEventListener("input", () => {
428
+ textarea.style.height = "auto";
429
+ textarea.style.height = `${textarea.scrollHeight}px`;
430
+ });
431
+
432
+ textarea.addEventListener("keydown", (e) => {
433
+ if (e.key === "Enter" && !e.shiftKey) {
434
+ e.preventDefault();
435
+ handleChat();
436
+ }
437
+ });
438
+
439
+ sendChatBtn.addEventListener("click", handleChat);
440
+ </script>
441
+ </body>
442
+ </html>
443
+