akhaliq HF Staff commited on
Commit
e83c351
·
verified ·
1 Parent(s): 44c2bbc

Upload folder using huggingface_hub

Browse files
Files changed (1) hide show
  1. index.html +1300 -19
index.html CHANGED
@@ -1,19 +1,1300 @@
1
- <!doctype html>
2
- <html>
3
- <head>
4
- <meta charset="utf-8" />
5
- <meta name="viewport" content="width=device-width" />
6
- <title>My static Space</title>
7
- <link rel="stylesheet" href="style.css" />
8
- </head>
9
- <body>
10
- <div class="card">
11
- <h1>Welcome to your static Space!</h1>
12
- <p>You can modify this app directly by editing <i>index.html</i> in the Files and versions tab.</p>
13
- <p>
14
- Also don't forget to check the
15
- <a href="https://huggingface.co/docs/hub/spaces" target="_blank">Spaces documentation</a>.
16
- </p>
17
- </div>
18
- </body>
19
- </html>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ <!DOCTYPE html>
2
+ <html lang="en">
3
+
4
+ <head>
5
+ <meta charset="UTF-8">
6
+ <meta name="viewport" content="width=device-width, initial-scale=1.0">
7
+ <title>TaskFlow - Modern Todo App</title>
8
+ <link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/font-awesome/6.4.0/css/all.min.css">
9
+ <style>
10
+ * {
11
+ margin: 0;
12
+ padding: 0;
13
+ box-sizing: border-box;
14
+ }
15
+
16
+ :root {
17
+ --primary: #6366f1;
18
+ --primary-dark: #4f46e5;
19
+ --secondary: #8b5cf6;
20
+ --success: #10b981;
21
+ --warning: #f59e0b;
22
+ --danger: #ef4444;
23
+ --dark: #1e293b;
24
+ --light: #f8fafc;
25
+ --text-primary: #1e293b;
26
+ --text-secondary: #64748b;
27
+ --border: #e2e8f0;
28
+ --shadow: rgba(0, 0, 0, 0.1);
29
+ --gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
30
+ --transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
31
+ }
32
+
33
+ body {
34
+ font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu, sans-serif;
35
+ background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
36
+ min-height: 100vh;
37
+ color: var(--text-primary);
38
+ transition: var(--transition);
39
+ }
40
+
41
+ body.dark-mode {
42
+ --light: #0f172a;
43
+ --text-primary: #f1f5f9;
44
+ --text-secondary: #94a3b8;
45
+ --border: #334155;
46
+ --shadow: rgba(0, 0, 0, 0.3);
47
+ background: linear-gradient(135deg, #1e293b 0%, #0f172a 100%);
48
+ }
49
+
50
+ .container {
51
+ max-width: 1200px;
52
+ margin: 0 auto;
53
+ padding: 20px;
54
+ }
55
+
56
+ header {
57
+ background: rgba(255, 255, 255, 0.95);
58
+ backdrop-filter: blur(10px);
59
+ border-radius: 20px;
60
+ padding: 25px;
61
+ margin-bottom: 30px;
62
+ box-shadow: 0 10px 40px var(--shadow);
63
+ animation: slideDown 0.5s ease-out;
64
+ }
65
+
66
+ body.dark-mode header {
67
+ background: rgba(30, 41, 59, 0.95);
68
+ }
69
+
70
+ .header-content {
71
+ display: flex;
72
+ justify-content: space-between;
73
+ align-items: center;
74
+ flex-wrap: wrap;
75
+ gap: 20px;
76
+ }
77
+
78
+ .logo {
79
+ display: flex;
80
+ align-items: center;
81
+ gap: 15px;
82
+ font-size: 28px;
83
+ font-weight: 800;
84
+ background: var(--gradient);
85
+ -webkit-background-clip: text;
86
+ -webkit-text-fill-color: transparent;
87
+ }
88
+
89
+ .logo i {
90
+ font-size: 32px;
91
+ -webkit-text-fill-color: var(--primary);
92
+ }
93
+
94
+ .header-actions {
95
+ display: flex;
96
+ gap: 15px;
97
+ align-items: center;
98
+ }
99
+
100
+ .theme-toggle {
101
+ background: var(--light);
102
+ border: 2px solid var(--border);
103
+ border-radius: 50px;
104
+ padding: 10px 15px;
105
+ cursor: pointer;
106
+ transition: var(--transition);
107
+ font-size: 20px;
108
+ }
109
+
110
+ .theme-toggle:hover {
111
+ transform: scale(1.1);
112
+ box-shadow: 0 5px 15px var(--shadow);
113
+ }
114
+
115
+ .main-content {
116
+ display: grid;
117
+ grid-template-columns: 1fr 350px;
118
+ gap: 30px;
119
+ animation: fadeIn 0.7s ease-out;
120
+ }
121
+
122
+ .todo-section {
123
+ background: rgba(255, 255, 255, 0.95);
124
+ backdrop-filter: blur(10px);
125
+ border-radius: 20px;
126
+ padding: 30px;
127
+ box-shadow: 0 10px 40px var(--shadow);
128
+ }
129
+
130
+ body.dark-mode .todo-section {
131
+ background: rgba(30, 41, 59, 0.95);
132
+ }
133
+
134
+ .add-todo-form {
135
+ display: flex;
136
+ gap: 10px;
137
+ margin-bottom: 30px;
138
+ }
139
+
140
+ .input-group {
141
+ flex: 1;
142
+ display: flex;
143
+ flex-direction: column;
144
+ gap: 5px;
145
+ }
146
+
147
+ .input-wrapper {
148
+ position: relative;
149
+ flex: 1;
150
+ }
151
+
152
+ .todo-input {
153
+ width: 100%;
154
+ padding: 15px 20px;
155
+ border: 2px solid var(--border);
156
+ border-radius: 15px;
157
+ font-size: 16px;
158
+ transition: var(--transition);
159
+ background: var(--light);
160
+ color: var(--text-primary);
161
+ }
162
+
163
+ .todo-input:focus {
164
+ outline: none;
165
+ border-color: var(--primary);
166
+ box-shadow: 0 0 0 3px rgba(99, 102, 241, 0.1);
167
+ }
168
+
169
+ .input-options {
170
+ display: flex;
171
+ gap: 10px;
172
+ margin-top: 10px;
173
+ flex-wrap: wrap;
174
+ }
175
+
176
+ .option-select {
177
+ padding: 8px 12px;
178
+ border: 1px solid var(--border);
179
+ border-radius: 10px;
180
+ background: var(--light);
181
+ color: var(--text-primary);
182
+ font-size: 14px;
183
+ cursor: pointer;
184
+ transition: var(--transition);
185
+ }
186
+
187
+ .option-select:focus {
188
+ outline: none;
189
+ border-color: var(--primary);
190
+ }
191
+
192
+ .add-btn {
193
+ padding: 15px 30px;
194
+ background: var(--gradient);
195
+ color: white;
196
+ border: none;
197
+ border-radius: 15px;
198
+ font-size: 16px;
199
+ font-weight: 600;
200
+ cursor: pointer;
201
+ transition: var(--transition);
202
+ display: flex;
203
+ align-items: center;
204
+ gap: 8px;
205
+ align-self: flex-end;
206
+ }
207
+
208
+ .add-btn:hover {
209
+ transform: translateY(-2px);
210
+ box-shadow: 0 10px 20px var(--shadow);
211
+ }
212
+
213
+ .filters {
214
+ display: flex;
215
+ gap: 10px;
216
+ margin-bottom: 25px;
217
+ flex-wrap: wrap;
218
+ }
219
+
220
+ .filter-btn {
221
+ padding: 10px 20px;
222
+ background: var(--light);
223
+ border: 2px solid var(--border);
224
+ border-radius: 12px;
225
+ cursor: pointer;
226
+ transition: var(--transition);
227
+ font-weight: 500;
228
+ color: var(--text-secondary);
229
+ }
230
+
231
+ .filter-btn.active {
232
+ background: var(--primary);
233
+ color: white;
234
+ border-color: var(--primary);
235
+ }
236
+
237
+ .filter-btn:hover:not(.active) {
238
+ border-color: var(--primary);
239
+ color: var(--primary);
240
+ }
241
+
242
+ .search-box {
243
+ position: relative;
244
+ flex: 1;
245
+ max-width: 300px;
246
+ }
247
+
248
+ .search-input {
249
+ width: 100%;
250
+ padding: 10px 15px 10px 40px;
251
+ border: 2px solid var(--border);
252
+ border-radius: 12px;
253
+ background: var(--light);
254
+ color: var(--text-primary);
255
+ }
256
+
257
+ .search-input:focus {
258
+ outline: none;
259
+ border-color: var(--primary);
260
+ }
261
+
262
+ .search-icon {
263
+ position: absolute;
264
+ left: 15px;
265
+ top: 50%;
266
+ transform: translateY(-50%);
267
+ color: var(--text-secondary);
268
+ }
269
+
270
+ .todo-list {
271
+ list-style: none;
272
+ max-height: 500px;
273
+ overflow-y: auto;
274
+ padding-right: 10px;
275
+ }
276
+
277
+ .todo-list::-webkit-scrollbar {
278
+ width: 8px;
279
+ }
280
+
281
+ .todo-list::-webkit-scrollbar-track {
282
+ background: var(--light);
283
+ border-radius: 10px;
284
+ }
285
+
286
+ .todo-list::-webkit-scrollbar-thumb {
287
+ background: var(--primary);
288
+ border-radius: 10px;
289
+ }
290
+
291
+ .todo-item {
292
+ background: var(--light);
293
+ border: 2px solid var(--border);
294
+ border-radius: 15px;
295
+ padding: 20px;
296
+ margin-bottom: 15px;
297
+ display: flex;
298
+ align-items: center;
299
+ gap: 15px;
300
+ transition: var(--transition);
301
+ cursor: move;
302
+ animation: slideIn 0.3s ease-out;
303
+ }
304
+
305
+ .todo-item:hover {
306
+ transform: translateX(5px);
307
+ box-shadow: 0 5px 15px var(--shadow);
308
+ }
309
+
310
+ .todo-item.completed {
311
+ opacity: 0.7;
312
+ }
313
+
314
+ .todo-item.completed .todo-text {
315
+ text-decoration: line-through;
316
+ color: var(--text-secondary);
317
+ }
318
+
319
+ .todo-item.dragging {
320
+ opacity: 0.5;
321
+ transform: rotate(2deg);
322
+ }
323
+
324
+ .checkbox-wrapper {
325
+ position: relative;
326
+ }
327
+
328
+ .todo-checkbox {
329
+ width: 24px;
330
+ height: 24px;
331
+ cursor: pointer;
332
+ accent-color: var(--success);
333
+ }
334
+
335
+ .todo-content {
336
+ flex: 1;
337
+ }
338
+
339
+ .todo-text {
340
+ font-size: 16px;
341
+ color: var(--text-primary);
342
+ margin-bottom: 8px;
343
+ }
344
+
345
+ .todo-meta {
346
+ display: flex;
347
+ gap: 10px;
348
+ flex-wrap: wrap;
349
+ }
350
+
351
+ .todo-category {
352
+ padding: 4px 10px;
353
+ background: var(--primary);
354
+ color: white;
355
+ border-radius: 20px;
356
+ font-size: 12px;
357
+ font-weight: 500;
358
+ }
359
+
360
+ .todo-priority {
361
+ padding: 4px 10px;
362
+ border-radius: 20px;
363
+ font-size: 12px;
364
+ font-weight: 500;
365
+ }
366
+
367
+ .priority-high {
368
+ background: var(--danger);
369
+ color: white;
370
+ }
371
+
372
+ .priority-medium {
373
+ background: var(--warning);
374
+ color: white;
375
+ }
376
+
377
+ .priority-low {
378
+ background: var(--success);
379
+ color: white;
380
+ }
381
+
382
+ .todo-date {
383
+ padding: 4px 10px;
384
+ background: var(--light);
385
+ border: 1px solid var(--border);
386
+ border-radius: 20px;
387
+ font-size: 12px;
388
+ color: var(--text-secondary);
389
+ display: flex;
390
+ align-items: center;
391
+ gap: 5px;
392
+ }
393
+
394
+ .todo-actions {
395
+ display: flex;
396
+ gap: 10px;
397
+ }
398
+
399
+ .action-btn {
400
+ width: 35px;
401
+ height: 35px;
402
+ border: none;
403
+ background: var(--light);
404
+ border-radius: 10px;
405
+ cursor: pointer;
406
+ transition: var(--transition);
407
+ color: var(--text-secondary);
408
+ display: flex;
409
+ align-items: center;
410
+ justify-content: center;
411
+ }
412
+
413
+ .action-btn:hover {
414
+ transform: scale(1.1);
415
+ }
416
+
417
+ .action-btn.edit:hover {
418
+ color: var(--primary);
419
+ background: rgba(99, 102, 241, 0.1);
420
+ }
421
+
422
+ .action-btn.delete:hover {
423
+ color: var(--danger);
424
+ background: rgba(239, 68, 68, 0.1);
425
+ }
426
+
427
+ .stats-section {
428
+ background: rgba(255, 255, 255, 0.95);
429
+ backdrop-filter: blur(10px);
430
+ border-radius: 20px;
431
+ padding: 30px;
432
+ box-shadow: 0 10px 40px var(--shadow);
433
+ }
434
+
435
+ body.dark-mode .stats-section {
436
+ background: rgba(30, 41, 59, 0.95);
437
+ }
438
+
439
+ .stats-header {
440
+ font-size: 20px;
441
+ font-weight: 700;
442
+ margin-bottom: 25px;
443
+ color: var(--text-primary);
444
+ }
445
+
446
+ .stat-card {
447
+ background: var(--light);
448
+ border-radius: 15px;
449
+ padding: 20px;
450
+ margin-bottom: 15px;
451
+ border: 2px solid var(--border);
452
+ transition: var(--transition);
453
+ }
454
+
455
+ .stat-card:hover {
456
+ transform: translateY(-3px);
457
+ box-shadow: 0 5px 15px var(--shadow);
458
+ }
459
+
460
+ .stat-label {
461
+ font-size: 14px;
462
+ color: var(--text-secondary);
463
+ margin-bottom: 8px;
464
+ }
465
+
466
+ .stat-value {
467
+ font-size: 32px;
468
+ font-weight: 700;
469
+ background: var(--gradient);
470
+ -webkit-background-clip: text;
471
+ -webkit-text-fill-color: transparent;
472
+ }
473
+
474
+ .progress-bar {
475
+ width: 100%;
476
+ height: 10px;
477
+ background: var(--border);
478
+ border-radius: 10px;
479
+ overflow: hidden;
480
+ margin-top: 15px;
481
+ }
482
+
483
+ .progress-fill {
484
+ height: 100%;
485
+ background: var(--gradient);
486
+ transition: width 0.5s ease;
487
+ }
488
+
489
+ .empty-state {
490
+ text-align: center;
491
+ padding: 60px 20px;
492
+ color: var(--text-secondary);
493
+ }
494
+
495
+ .empty-state i {
496
+ font-size: 64px;
497
+ margin-bottom: 20px;
498
+ opacity: 0.5;
499
+ }
500
+
501
+ .empty-state h3 {
502
+ font-size: 24px;
503
+ margin-bottom: 10px;
504
+ color: var(--text-primary);
505
+ }
506
+
507
+ .export-import {
508
+ display: flex;
509
+ gap: 10px;
510
+ margin-top: 20px;
511
+ }
512
+
513
+ .export-btn,
514
+ .import-btn {
515
+ flex: 1;
516
+ padding: 12px;
517
+ background: var(--light);
518
+ border: 2px solid var(--border);
519
+ border-radius: 12px;
520
+ cursor: pointer;
521
+ transition: var(--transition);
522
+ font-weight: 500;
523
+ color: var(--text-primary);
524
+ }
525
+
526
+ .export-btn:hover,
527
+ .import-btn:hover {
528
+ border-color: var(--primary);
529
+ color: var(--primary);
530
+ }
531
+
532
+ .modal {
533
+ display: none;
534
+ position: fixed;
535
+ top: 0;
536
+ left: 0;
537
+ width: 100%;
538
+ height: 100%;
539
+ background: rgba(0, 0, 0, 0.5);
540
+ backdrop-filter: blur(5px);
541
+ z-index: 1000;
542
+ animation: fadeIn 0.3s ease;
543
+ }
544
+
545
+ .modal.active {
546
+ display: flex;
547
+ align-items: center;
548
+ justify-content: center;
549
+ }
550
+
551
+ .modal-content {
552
+ background: var(--light);
553
+ border-radius: 20px;
554
+ padding: 30px;
555
+ max-width: 500px;
556
+ width: 90%;
557
+ animation: slideUp 0.3s ease;
558
+ }
559
+
560
+ .modal-header {
561
+ font-size: 24px;
562
+ font-weight: 700;
563
+ margin-bottom: 20px;
564
+ color: var(--text-primary);
565
+ }
566
+
567
+ .modal-body {
568
+ margin-bottom: 20px;
569
+ }
570
+
571
+ .modal-input {
572
+ width: 100%;
573
+ padding: 12px;
574
+ border: 2px solid var(--border);
575
+ border-radius: 12px;
576
+ background: var(--light);
577
+ color: var(--text-primary);
578
+ margin-bottom: 15px;
579
+ }
580
+
581
+ .modal-input:focus {
582
+ outline: none;
583
+ border-color: var(--primary);
584
+ }
585
+
586
+ .modal-footer {
587
+ display: flex;
588
+ gap: 10px;
589
+ justify-content: flex-end;
590
+ }
591
+
592
+ .modal-btn {
593
+ padding: 10px 20px;
594
+ border: none;
595
+ border-radius: 10px;
596
+ cursor: pointer;
597
+ font-weight: 500;
598
+ transition: var(--transition);
599
+ }
600
+
601
+ .modal-btn.cancel {
602
+ background: var(--border);
603
+ color: var(--text-primary);
604
+ }
605
+
606
+ .modal-btn.save {
607
+ background: var(--primary);
608
+ color: white;
609
+ }
610
+
611
+ .modal-btn:hover {
612
+ transform: translateY(-2px);
613
+ box-shadow: 0 5px 15px var(--shadow);
614
+ }
615
+
616
+ .keyboard-shortcuts {
617
+ position: fixed;
618
+ bottom: 20px;
619
+ right: 20px;
620
+ background: var(--light);
621
+ padding: 15px;
622
+ border-radius: 15px;
623
+ border: 2px solid var(--border);
624
+ font-size: 12px;
625
+ color: var(--text-secondary);
626
+ box-shadow: 0 5px 15px var(--shadow);
627
+ max-width: 200px;
628
+ }
629
+
630
+ .shortcut-item {
631
+ margin-bottom: 8px;
632
+ display: flex;
633
+ justify-content: space-between;
634
+ }
635
+
636
+ .shortcut-key {
637
+ background: var(--border);
638
+ padding: 2px 6px;
639
+ border-radius: 4px;
640
+ font-weight: 600;
641
+ color: var(--text-primary);
642
+ }
643
+
644
+ @keyframes slideDown {
645
+ from {
646
+ opacity: 0;
647
+ transform: translateY(-20px);
648
+ }
649
+
650
+ to {
651
+ opacity: 1;
652
+ transform: translateY(0);
653
+ }
654
+ }
655
+
656
+ @keyframes fadeIn {
657
+ from {
658
+ opacity: 0;
659
+ }
660
+
661
+ to {
662
+ opacity: 1;
663
+ }
664
+ }
665
+
666
+ @keyframes slideIn {
667
+ from {
668
+ opacity: 0;
669
+ transform: translateX(-20px);
670
+ }
671
+
672
+ to {
673
+ opacity: 1;
674
+ transform: translateX(0);
675
+ }
676
+ }
677
+
678
+ @keyframes slideUp {
679
+ from {
680
+ opacity: 0;
681
+ transform: translateY(20px);
682
+ }
683
+
684
+ to {
685
+ opacity: 1;
686
+ transform: translateY(0);
687
+ }
688
+ }
689
+
690
+ @media (max-width: 768px) {
691
+ .main-content {
692
+ grid-template-columns: 1fr;
693
+ }
694
+
695
+ .add-todo-form {
696
+ flex-direction: column;
697
+ }
698
+
699
+ .add-btn {
700
+ width: 100%;
701
+ justify-content: center;
702
+ }
703
+
704
+ .header-content {
705
+ flex-direction: column;
706
+ text-align: center;
707
+ }
708
+
709
+ .keyboard-shortcuts {
710
+ display: none;
711
+ }
712
+
713
+ .filters {
714
+ justify-content: center;
715
+ }
716
+
717
+ .search-box {
718
+ max-width: 100%;
719
+ }
720
+ }
721
+
722
+ .built-with {
723
+ position: fixed;
724
+ bottom: 10px;
725
+ left: 50%;
726
+ transform: translateX(-50%);
727
+ color: white;
728
+ font-size: 12px;
729
+ opacity: 0.8;
730
+ z-index: 100;
731
+ }
732
+
733
+ .built-with a {
734
+ color: white;
735
+ text-decoration: none;
736
+ font-weight: 600;
737
+ }
738
+
739
+ .built-with a:hover {
740
+ text-decoration: underline;
741
+ }
742
+ </style>
743
+ </head>
744
+
745
+ <body>
746
+ <div class="container">
747
+ <header>
748
+ <div class="header-content">
749
+ <div class="logo">
750
+ <i class="fas fa-tasks"></i>
751
+ TaskFlow
752
+ </div>
753
+ <div class="header-actions">
754
+ <button class="theme-toggle" onclick="toggleTheme()">
755
+ <i class="fas fa-moon"></i>
756
+ </button>
757
+ </div>
758
+ </div>
759
+ </header>
760
+
761
+ <main class="main-content">
762
+ <section class="todo-section">
763
+ <form class="add-todo-form" onsubmit="addTodo(event)">
764
+ <div class="input-group">
765
+ <div class="input-wrapper">
766
+ <input type="text" class="todo-input" id="todoInput" placeholder="What needs to be done?" required>
767
+ </div>
768
+ <div class="input-options">
769
+ <select class="option-select" id="categorySelect">
770
+ <option value="personal">Personal</option>
771
+ <option value="work">Work</option>
772
+ <option value="shopping">Shopping</option>
773
+ <option value="health">Health</option>
774
+ <option value="other">Other</option>
775
+ </select>
776
+ <select class="option-select" id="prioritySelect">
777
+ <option value="low">Low Priority</option>
778
+ <option value="medium">Medium Priority</option>
779
+ <option value="high">High Priority</option>
780
+ </select>
781
+ <input type="date" class="option-select" id="dueDateSelect">
782
+ </div>
783
+ </div>
784
+ <button type="submit" class="add-btn">
785
+ <i class="fas fa-plus"></i>
786
+ Add Task
787
+ </button>
788
+ </form>
789
+
790
+ <div class="filters">
791
+ <button class="filter-btn active" onclick="filterTodos('all')">All Tasks</button>
792
+ <button class="filter-btn" onclick="filterTodos('active')">Active</button>
793
+ <button class="filter-btn" onclick="filterTodos('completed')">Completed</button>
794
+ <div class="search-box">
795
+ <i class="fas fa-search search-icon"></i>
796
+ <input type="text" class="search-input" id="searchInput" placeholder="Search tasks..." oninput="searchTodos()">
797
+ </div>
798
+ </div>
799
+
800
+ <ul class="todo-list" id="todoList">
801
+ <!-- Todos will be dynamically added here -->
802
+ </ul>
803
+
804
+ <div class="empty-state" id="emptyState" style="display: none;">
805
+ <i class="fas fa-clipboard-list"></i>
806
+ <h3>No tasks yet</h3>
807
+ <p>Add your first task to get started!</p>
808
+ </div>
809
+ </section>
810
+
811
+ <aside class="stats-section">
812
+ <h2 class="stats-header">Statistics</h2>
813
+
814
+ <div class="stat-card">
815
+ <div class="stat-label">Total Tasks</div>
816
+ <div class="stat-value" id="totalTasks">0</div>
817
+ </div>
818
+
819
+ <div class="stat-card">
820
+ <div class="stat-label">Completed</div>
821
+ <div class="stat-value" id="completedTasks">0</div>
822
+ </div>
823
+
824
+ <div class="stat-card">
825
+ <div class="stat-label">Active</div>
826
+ <div class="stat-value" id="activeTasks">0</div>
827
+ </div>
828
+
829
+ <div class="stat-card">
830
+ <div class="stat-label">Completion Rate</div>
831
+ <div class="stat-value" id="completionRate">0%</div>
832
+ <div class="progress-bar">
833
+ <div class="progress-fill" id="progressFill" style="width: 0%"></div>
834
+ </div>
835
+ </div>
836
+
837
+ <div class="export-import">
838
+ <button class="export-btn" onclick="exportTodos()">
839
+ <i class="fas fa-download"></i> Export
840
+ </button>
841
+ <button class="import-btn" onclick="document.getElementById('importFile').click()">
842
+ <i class="fas fa-upload"></i> Import
843
+ </button>
844
+ <input type="file" id="importFile" style="display: none;" accept=".json" onchange="importTodos(event)">
845
+ </div>
846
+ </aside>
847
+ </main>
848
+ </div>
849
+
850
+ <div class="keyboard-shortcuts">
851
+ <div style="font-weight: 600; margin-bottom: 10px;">Shortcuts</div>
852
+ <div class="shortcut-item">
853
+ <span>New Task</span>
854
+ <span class="shortcut-key">Ctrl+N</span>
855
+ </div>
856
+ <div class="shortcut-item">
857
+ <span>Search</span>
858
+ <span class="shortcut-key">Ctrl+F</span>
859
+ </div>
860
+ <div class="shortcut-item">
861
+ <span>Clear All</span>
862
+ <span class="shortcut-key">Ctrl+D</span>
863
+ </div>
864
+ </div>
865
+
866
+ <div class="built-with">
867
+ Built with <a href="https://huggingface.co/spaces/akhaliq/anycoder" target="_blank">anycoder</a>
868
+ </div>
869
+
870
+ <div class="modal" id="editModal">
871
+ <div class="modal-content">
872
+ <div class="modal-header">Edit Task</div>
873
+ <div class="modal-body">
874
+ <input type="text" class="modal-input" id="editInput" placeholder="Task text">
875
+ <select class="modal-input" id="editCategory">
876
+ <option value="personal">Personal</option>
877
+ <option value="work">Work</option>
878
+ <option value="shopping">Shopping</option>
879
+ <option value="health">Health</option>
880
+ <option value="other">Other</option>
881
+ </select>
882
+ <select class="modal-input" id="editPriority">
883
+ <option value="low">Low Priority</option>
884
+ <option value="medium">Medium Priority</option>
885
+ <option value="high">High Priority</option>
886
+ </select>
887
+ <input type="date" class="modal-input" id="editDueDate">
888
+ </div>
889
+ <div class="modal-footer">
890
+ <button class="modal-btn cancel" onclick="closeEditModal()">Cancel</button>
891
+ <button class="modal-btn save" onclick="saveEdit()">Save</button>
892
+ </div>
893
+ </div>
894
+ </div>
895
+
896
+ <script>
897
+ let todos = JSON.parse(localStorage.getItem('todos')) || [];
898
+ let currentFilter = 'all';
899
+ let editingTodoId = null;
900
+ let draggedItem = null;
901
+
902
+ function initializeApp() {
903
+ renderTodos();
904
+ updateStats();
905
+ setupKeyboardShortcuts();
906
+ setupDragAndDrop();
907
+
908
+ // Check for dark mode preference
909
+ if (localStorage.getItem('darkMode') === 'true') {
910
+ document.body.classList.add('dark-mode');
911
+ document.querySelector('.theme-toggle i').classList.replace('fa-moon', 'fa-sun');
912
+ }
913
+ }
914
+
915
+ function addTodo(event) {
916
+ event.preventDefault();
917
+
918
+ const input = document.getElementById('todoInput');
919
+ const category = document.getElementById('categorySelect').value;
920
+ const priority = document.getElementById('prioritySelect').value;
921
+ const dueDate = document.getElementById('dueDateSelect').value;
922
+
923
+ const todo = {
924
+ id: Date.now(),
925
+ text: input.value,
926
+ completed: false,
927
+ category: category,
928
+ priority: priority,
929
+ dueDate: dueDate,
930
+ createdAt: new Date().toISOString()
931
+ };
932
+
933
+ todos.unshift(todo);
934
+ saveTodos();
935
+ renderTodos();
936
+ updateStats();
937
+
938
+ // Reset form
939
+ input.value = '';
940
+ document.getElementById('dueDateSelect').value = '';
941
+
942
+ // Animation
943
+ showNotification('Task added successfully!');
944
+ }
945
+
946
+ function toggleTodo(id) {
947
+ const todo = todos.find(t => t.id === id);
948
+ if (todo) {
949
+ todo.completed = !todo.completed;
950
+ saveTodos();
951
+ renderTodos();
952
+ updateStats();
953
+ }
954
+ }
955
+
956
+ function deleteTodo(id) {
957
+ todos = todos.filter(t => t.id !== id);
958
+ saveTodos();
959
+ renderTodos();
960
+ updateStats();
961
+ showNotification('Task deleted!');
962
+ }
963
+
964
+ function editTodo(id) {
965
+ const todo = todos.find(t => t.id === id);
966
+ if (todo) {
967
+ editingTodoId = id;
968
+ document.getElementById('editInput').value = todo.text;
969
+ document.getElementById('editCategory').value = todo.category;
970
+ document.getElementById('editPriority').value = todo.priority;
971
+ document.getElementById('editDueDate').value = todo.dueDate || '';
972
+ document.getElementById('editModal').classList.add('active');
973
+ }
974
+ }
975
+
976
+ function closeEditModal() {
977
+ document.getElementById('editModal').classList.remove('active');
978
+ editingTodoId = null;
979
+ }
980
+
981
+ function saveEdit() {
982
+ const todo = todos.find(t => t.id === editingTodoId);
983
+ if (todo) {
984
+ todo.text = document.getElementById('editInput').value;
985
+ todo.category = document.getElementById('editCategory').value;
986
+ todo.priority = document.getElementById('editPriority').value;
987
+ todo.dueDate = document.getElementById('editDueDate').value;
988
+ saveTodos();
989
+ renderTodos();
990
+ updateStats();
991
+ closeEditModal();
992
+ showNotification('Task updated!');
993
+ }
994
+ }
995
+
996
+ function filterTodos(filter) {
997
+ currentFilter = filter;
998
+
999
+ // Update active button
1000
+ document.querySelectorAll('.filter-btn').forEach(btn => {
1001
+ btn.classList.remove('active');
1002
+ });
1003
+ event.target.classList.add('active');
1004
+
1005
+ renderTodos();
1006
+ }
1007
+
1008
+ function searchTodos() {
1009
+ const searchTerm = document.getElementById('searchInput').value.toLowerCase();
1010
+ renderTodos(searchTerm);
1011
+ }
1012
+
1013
+ function renderTodos(searchTerm = '') {
1014
+ const todoList = document.getElementById('todoList');
1015
+ const emptyState = document.getElementById('emptyState');
1016
+
1017
+ let filteredTodos = todos;
1018
+
1019
+ // Apply filter
1020
+ if (currentFilter === 'active') {
1021
+ filteredTodos = todos.filter(t => !t.completed);
1022
+ } else if (currentFilter === 'completed') {
1023
+ filteredTodos = todos.filter(t => t.completed);
1024
+ }
1025
+
1026
+ // Apply search
1027
+ if (searchTerm) {
1028
+ filteredTodos = filteredTodos.filter(t =>
1029
+ t.text.toLowerCase().includes(searchTerm) ||
1030
+ t.category.toLowerCase().includes(searchTerm)
1031
+ );
1032
+ }
1033
+
1034
+ if (filteredTodos.length === 0) {
1035
+ todoList.style.display = 'none';
1036
+ emptyState.style.display = 'block';
1037
+ } else {
1038
+ todoList.style.display = 'block';
1039
+ emptyState.style.display = 'none';
1040
+
1041
+ todoList.innerHTML = filteredTodos.map(todo => `
1042
+ <li class="todo-item ${todo.completed ? 'completed' : ''}" draggable="true" data-id="${todo.id}">
1043
+ <div class="checkbox-wrapper">
1044
+ <input type="checkbox" class="todo-checkbox"
1045
+ ${todo.completed ? 'checked' : ''}
1046
+ onchange="toggleTodo(${todo.id})">
1047
+ </div>
1048
+ <div class="todo-content">
1049
+ <div class="todo-text">${escapeHtml(todo.text)}</div>
1050
+ <div class="todo-meta">
1051
+ <span class="todo-category">${todo.category}</span>
1052
+ <span class="todo-priority priority-${todo.priority}">${todo.priority}</span>
1053
+ ${todo.dueDate ? `
1054
+ <span class="todo-date">
1055
+ <i class="fas fa-calendar"></i>
1056
+ ${formatDate(todo.dueDate)}
1057
+ </span>
1058
+ ` : ''}
1059
+ </div>
1060
+ </div>
1061
+ <div class="todo-actions">
1062
+ <button class="action-btn edit" onclick="editTodo(${todo.id})">
1063
+ <i class="fas fa-edit"></i>
1064
+ </button>
1065
+ <button class="action-btn delete" onclick="deleteTodo(${todo.id})">
1066
+ <i class="fas fa-trash"></i>
1067
+ </button>
1068
+ </div>
1069
+ </li>
1070
+ `).join('');
1071
+ }
1072
+
1073
+ setupDragAndDrop();
1074
+ }
1075
+
1076
+ function setupDragAndDrop() {
1077
+ const items = document.querySelectorAll('.todo-item');
1078
+
1079
+ items.forEach(item => {
1080
+ item.addEventListener('dragstart', handleDragStart);
1081
+ item.addEventListener('dragend', handleDragEnd);
1082
+ item.addEventListener('dragover', handleDragOver);
1083
+ item.addEventListener('drop', handleDrop);
1084
+ });
1085
+ }
1086
+
1087
+ function handleDragStart(e) {
1088
+ draggedItem = this;
1089
+ this.classList.add('dragging');
1090
+ e.dataTransfer.effectAllowed = 'move';
1091
+ e.dataTransfer.setData('text/html', this.innerHTML);
1092
+ }
1093
+
1094
+ function handleDragEnd(e) {
1095
+ this.classList.remove('dragging');
1096
+ draggedItem = null;
1097
+ }
1098
+
1099
+ function handleDragOver(e) {
1100
+ if (e.preventDefault) {
1101
+ e.preventDefault();
1102
+ }
1103
+ e.dataTransfer.dropEffect = 'move';
1104
+
1105
+ const afterElement = getDragAfterElement(document.getElementById('todoList'), e.clientY);
1106
+ if (afterElement == null) {
1107
+ document.getElementById('todoList').appendChild(draggedItem);
1108
+ } else {
1109
+ document.getElementById('todoList').insertBefore(draggedItem, afterElement);
1110
+ }
1111
+
1112
+ return false;
1113
+ }
1114
+
1115
+ function handleDrop(e) {
1116
+ if (e.stopPropagation) {
1117
+ e.stopPropagation();
1118
+ }
1119
+
1120
+ // Update todos order
1121
+ const newOrder = Array.from(document.querySelectorAll('.todo-item')).map(item =>
1122
+ parseInt(item.dataset.id)
1123
+ );
1124
+
1125
+ const reorderedTodos = [];
1126
+ newOrder.forEach(id => {
1127
+ const todo = todos.find(t => t.id === id);
1128
+ if (todo) reorderedTodos.push(todo);
1129
+ });
1130
+
1131
+ todos = reorderedTodos;
1132
+ saveTodos();
1133
+
1134
+ return false;
1135
+ }
1136
+
1137
+ function getDragAfterElement(container, y) {
1138
+ const draggableElements = [...container.querySelectorAll('.todo-item:not(.dragging)')];
1139
+
1140
+ return draggableElements.reduce((closest, child) => {
1141
+ const box = child.getBoundingClientRect();
1142
+ const offset = y - box.top - box.height / 2;
1143
+
1144
+ if (offset < 0 && offset > closest.offset) {
1145
+ return { offset: offset, element: child };
1146
+ } else {
1147
+ return closest;
1148
+ }
1149
+ }, { offset: Number.NEGATIVE_INFINITY }).element;
1150
+ }
1151
+
1152
+ function updateStats() {
1153
+ const total = todos.length;
1154
+ const completed = todos.filter(t => t.completed).length;
1155
+ const active = total - completed;
1156
+ const rate = total > 0 ? Math.round((completed / total) * 100) : 0;
1157
+
1158
+ document.getElementById('totalTasks').textContent = total;
1159
+ document.getElementById('completedTasks').textContent = completed;
1160
+ document.getElementById('activeTasks').textContent = active;
1161
+ document.getElementById('completionRate').textContent = rate + '%';
1162
+ document.getElementById('progressFill').style.width = rate + '%';
1163
+ }
1164
+
1165
+ function toggleTheme() {
1166
+ document.body.classList.toggle('dark-mode');
1167
+ const isDark = document.body.classList.contains('dark-mode');
1168
+ localStorage.setItem('darkMode', isDark);
1169
+
1170
+ const icon = document.querySelector('.theme-toggle i');
1171
+ if (isDark) {
1172
+ icon.classList.replace('fa-moon', 'fa-sun');
1173
+ } else {
1174
+ icon.classList.replace('fa-sun', 'fa-moon');
1175
+ }
1176
+ }
1177
+
1178
+ function exportTodos() {
1179
+ const dataStr = JSON.stringify(todos, null, 2);
1180
+ const dataUri = 'data:application/json;charset=utf-8,'+ encodeURIComponent(dataStr);
1181
+
1182
+ const exportFileDefaultName = `todos_${new Date().toISOString().split('T')[0]}.json`;
1183
+
1184
+ const linkElement = document.createElement('a');
1185
+ linkElement.setAttribute('href', dataUri);
1186
+ linkElement.setAttribute('download', exportFileDefaultName);
1187
+ linkElement.click();
1188
+
1189
+ showNotification('Tasks exported!');
1190
+ }
1191
+
1192
+ function importTodos(event) {
1193
+ const file = event.target.files[0];
1194
+ if (file) {
1195
+ const reader = new FileReader();
1196
+ reader.onload = function(e) {
1197
+ try {
1198
+ todos = JSON.parse(e.target.result);
1199
+ saveTodos();
1200
+ renderTodos();
1201
+ updateStats();
1202
+ showNotification('Tasks imported successfully!');
1203
+ } catch (error) {
1204
+ showNotification('Error importing file!', 'error');
1205
+ }
1206
+ };
1207
+ reader.readAsText(file);
1208
+ }
1209
+ }
1210
+
1211
+ function saveTodos() {
1212
+ localStorage.setItem('todos', JSON.stringify(todos));
1213
+ }
1214
+
1215
+ function escapeHtml(text) {
1216
+ const map = {
1217
+ '&': '&amp;',
1218
+ '<': '&lt;',
1219
+ '>': '&gt;',
1220
+ '"': '&quot;',
1221
+ "'": '&#039;'
1222
+ };
1223
+ return text.replace(/[&<>"']/g, m => map[m]);
1224
+ }
1225
+
1226
+ function formatDate(dateStr) {
1227
+ const date = new Date(dateStr);
1228
+ const today = new Date();
1229
+ const tomorrow = new Date(today);
1230
+ tomorrow.setDate(tomorrow.getDate() + 1);
1231
+
1232
+ if (date.toDateString() === today.toDateString()) {
1233
+ return 'Today';
1234
+ } else if (date.toDateString() === tomorrow.toDateString()) {
1235
+ return 'Tomorrow';
1236
+ } else {
1237
+ return date.toLocaleDateString('en-US', { month: 'short', day: 'numeric' });
1238
+ }
1239
+ }
1240
+
1241
+ function showNotification(message, type = 'success') {
1242
+ const notification = document.createElement('div');
1243
+ notification.style.cssText = `
1244
+ position: fixed;
1245
+ top: 20px;
1246
+ right: 20px;
1247
+ padding: 15px 20px;
1248
+ background: ${type === 'success' ? 'var(--success)' : 'var(--danger)'};
1249
+ color: white;
1250
+ border-radius: 10px;
1251
+ box-shadow: 0 5px 15px var(--shadow);
1252
+ z-index: 2000;
1253
+ animation: slideIn 0.3s ease;
1254
+ `;
1255
+ notification.textContent = message;
1256
+ document.body.appendChild(notification);
1257
+
1258
+ setTimeout(() => {
1259
+ notification.style.animation = 'fadeOut 0.3s ease';
1260
+ setTimeout(() => notification.remove(), 300);
1261
+ }, 3000);
1262
+ }
1263
+
1264
+ function setupKeyboardShortcuts() {
1265
+ document.addEventListener('keydown', (e) => {
1266
+ // Ctrl+N - New task
1267
+ if (e.ctrlKey && e.key === 'n') {
1268
+ e.preventDefault();
1269
+ document.getElementById('todoInput').focus();
1270
+ }
1271
+
1272
+ // Ctrl+F - Search
1273
+ if (e.ctrlKey && e.key === 'f') {
1274
+ e.preventDefault();
1275
+ document.getElementById('searchInput').focus();
1276
+ }
1277
+
1278
+ // Ctrl+D - Clear completed
1279
+ if (e.ctrlKey && e.key === 'd') {
1280
+ e.preventDefault();
1281
+ todos = todos.filter(t => !t.completed);
1282
+ saveTodos();
1283
+ renderTodos();
1284
+ updateStats();
1285
+ showNotification('Completed tasks cleared!');
1286
+ }
1287
+
1288
+ // Escape - Close modal
1289
+ if (e.key === 'Escape') {
1290
+ closeEditModal();
1291
+ }
1292
+ });
1293
+ }
1294
+
1295
+ // Initialize app on load
1296
+ document.addEventListener('DOMContentLoaded', initializeApp);
1297
+ </script>
1298
+ </body>
1299
+
1300
+ </html>