Phierru commited on
Commit
25950f1
·
verified ·
1 Parent(s): c5cc069

Upload folder using huggingface_hub

Browse files
Files changed (1) hide show
  1. index.html +805 -19
index.html CHANGED
@@ -1,19 +1,805 @@
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>Professional Portrait Creator | Qwen Image Edit</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
+ font-family: 'Segoe UI', system-ui, -apple-system, sans-serif;
15
+ }
16
+
17
+ :root {
18
+ --primary: #2563eb;
19
+ --primary-dark: #1d4ed8;
20
+ --secondary: #64748b;
21
+ --accent: #f59e0b;
22
+ --light: #f8fafc;
23
+ --dark: #1e293b;
24
+ --success: #10b981;
25
+ --shadow: 0 10px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04);
26
+ }
27
+
28
+ body {
29
+ background: linear-gradient(135deg, #f0f9ff 0%, #e0f2fe 100%);
30
+ color: var(--dark);
31
+ line-height: 1.6;
32
+ min-height: 100vh;
33
+ padding: 1rem;
34
+ }
35
+
36
+ .container {
37
+ max-width: 1200px;
38
+ margin: 0 auto;
39
+ }
40
+
41
+ header {
42
+ display: flex;
43
+ justify-content: space-between;
44
+ align-items: center;
45
+ padding: 1.5rem 0;
46
+ margin-bottom: 2rem;
47
+ }
48
+
49
+ .logo {
50
+ display: flex;
51
+ align-items: center;
52
+ gap: 0.75rem;
53
+ font-size: 1.5rem;
54
+ font-weight: 700;
55
+ color: var(--primary);
56
+ }
57
+
58
+ .logo i {
59
+ font-size: 1.75rem;
60
+ }
61
+
62
+ .built-with {
63
+ font-size: 0.875rem;
64
+ color: var(--secondary);
65
+ }
66
+
67
+ .built-with a {
68
+ color: var(--primary);
69
+ text-decoration: none;
70
+ transition: color 0.3s;
71
+ }
72
+
73
+ .built-with a:hover {
74
+ color: var(--primary-dark);
75
+ text-decoration: underline;
76
+ }
77
+
78
+ main {
79
+ display: grid;
80
+ grid-template-columns: 1fr;
81
+ gap: 2rem;
82
+ }
83
+
84
+ @media (min-width: 768px) {
85
+ main {
86
+ grid-template-columns: 1fr 1fr;
87
+ }
88
+ }
89
+
90
+ .card {
91
+ background: white;
92
+ border-radius: 1rem;
93
+ padding: 2rem;
94
+ box-shadow: var(--shadow);
95
+ transition: transform 0.3s, box-shadow 0.3s;
96
+ }
97
+
98
+ .card:hover {
99
+ transform: translateY(-5px);
100
+ box-shadow: 0 20px 40px -10px rgba(0, 0, 0, 0.15);
101
+ }
102
+
103
+ .card-title {
104
+ font-size: 1.25rem;
105
+ font-weight: 600;
106
+ margin-bottom: 1rem;
107
+ color: var(--primary);
108
+ display: flex;
109
+ align-items: center;
110
+ gap: 0.5rem;
111
+ }
112
+
113
+ .upload-area {
114
+ border: 2px dashed #cbd5e1;
115
+ border-radius: 0.75rem;
116
+ padding: 3rem 1.5rem;
117
+ text-align: center;
118
+ cursor: pointer;
119
+ transition: all 0.3s;
120
+ margin-bottom: 1.5rem;
121
+ background: #f8fafc;
122
+ }
123
+
124
+ .upload-area:hover {
125
+ border-color: var(--primary);
126
+ background: #f0f9ff;
127
+ }
128
+
129
+ .upload-area.active {
130
+ border-color: var(--primary);
131
+ background: #dbeafe;
132
+ }
133
+
134
+ .upload-icon {
135
+ font-size: 3rem;
136
+ color: var(--secondary);
137
+ margin-bottom: 1rem;
138
+ }
139
+
140
+ .upload-text {
141
+ color: var(--secondary);
142
+ margin-bottom: 0.5rem;
143
+ }
144
+
145
+ .upload-button {
146
+ background: var(--primary);
147
+ color: white;
148
+ border: none;
149
+ padding: 0.75rem 1.5rem;
150
+ border-radius: 0.5rem;
151
+ font-weight: 500;
152
+ cursor: pointer;
153
+ transition: background 0.3s;
154
+ display: inline-flex;
155
+ align-items: center;
156
+ gap: 0.5rem;
157
+ }
158
+
159
+ .upload-button:hover {
160
+ background: var(--primary-dark);
161
+ }
162
+
163
+ .preview-container {
164
+ margin-top: 1.5rem;
165
+ display: none;
166
+ }
167
+
168
+ .preview-title {
169
+ font-size: 1rem;
170
+ font-weight: 500;
171
+ margin-bottom: 0.5rem;
172
+ color: var(--secondary);
173
+ }
174
+
175
+ .preview-image {
176
+ width: 100%;
177
+ max-width: 300px;
178
+ border-radius: 0.5rem;
179
+ box-shadow: 0 4px 6px -1px rgba(0, 0, 0, 0.1);
180
+ }
181
+
182
+ .options {
183
+ margin-top: 1.5rem;
184
+ }
185
+
186
+ .option-group {
187
+ margin-bottom: 1.5rem;
188
+ }
189
+
190
+ .option-label {
191
+ display: block;
192
+ font-weight: 500;
193
+ margin-bottom: 0.5rem;
194
+ color: var(--dark);
195
+ }
196
+
197
+ .slider-container {
198
+ display: flex;
199
+ align-items: center;
200
+ gap: 1rem;
201
+ }
202
+
203
+ .slider {
204
+ flex: 1;
205
+ -webkit-appearance: none;
206
+ width: 100%;
207
+ height: 8px;
208
+ border-radius: 4px;
209
+ background: #e2e8f0;
210
+ outline: none;
211
+ }
212
+
213
+ .slider::-webkit-slider-thumb {
214
+ -webkit-appearance: none;
215
+ appearance: none;
216
+ width: 20px;
217
+ height: 20px;
218
+ border-radius: 50%;
219
+ background: var(--primary);
220
+ cursor: pointer;
221
+ box-shadow: 0 2px 4px rgba(0, 0, 0, 0.2);
222
+ }
223
+
224
+ .slider-value {
225
+ font-weight: 600;
226
+ color: var(--primary);
227
+ min-width: 40px;
228
+ text-align: center;
229
+ }
230
+
231
+ .button-group {
232
+ display: flex;
233
+ gap: 1rem;
234
+ margin-top: 2rem;
235
+ }
236
+
237
+ .btn {
238
+ padding: 0.875rem 1.5rem;
239
+ border-radius: 0.5rem;
240
+ font-weight: 500;
241
+ cursor: pointer;
242
+ transition: all 0.3s;
243
+ display: inline-flex;
244
+ align-items: center;
245
+ gap: 0.5rem;
246
+ flex: 1;
247
+ justify-content: center;
248
+ }
249
+
250
+ .btn-primary {
251
+ background: var(--primary);
252
+ color: white;
253
+ border: none;
254
+ }
255
+
256
+ .btn-primary:hover {
257
+ background: var(--primary-dark);
258
+ }
259
+
260
+ .btn-secondary {
261
+ background: white;
262
+ color: var(--primary);
263
+ border: 1px solid var(--primary);
264
+ }
265
+
266
+ .btn-secondary:hover {
267
+ background: #f0f9ff;
268
+ }
269
+
270
+ .result-container {
271
+ display: none;
272
+ text-align: center;
273
+ }
274
+
275
+ .result-title {
276
+ font-size: 1.25rem;
277
+ font-weight: 600;
278
+ margin-bottom: 1rem;
279
+ color: var(--success);
280
+ }
281
+
282
+ .result-image {
283
+ width: 100%;
284
+ max-width: 400px;
285
+ border-radius: 0.75rem;
286
+ box-shadow: var(--shadow);
287
+ margin-bottom: 1.5rem;
288
+ }
289
+
290
+ .loading {
291
+ display: none;
292
+ text-align: center;
293
+ padding: 2rem;
294
+ }
295
+
296
+ .loading-spinner {
297
+ width: 50px;
298
+ height: 50px;
299
+ border: 5px solid #e2e8f0;
300
+ border-top: 5px solid var(--primary);
301
+ border-radius: 50%;
302
+ animation: spin 1s linear infinite;
303
+ margin: 0 auto 1rem;
304
+ }
305
+
306
+ @keyframes spin {
307
+ 0% {
308
+ transform: rotate(0deg);
309
+ }
310
+
311
+ 100% {
312
+ transform: rotate(360deg);
313
+ }
314
+ }
315
+
316
+ .feature-list {
317
+ list-style: none;
318
+ margin-top: 1.5rem;
319
+ }
320
+
321
+ .feature-list li {
322
+ padding: 0.5rem 0;
323
+ display: flex;
324
+ align-items: center;
325
+ gap: 0.75rem;
326
+ }
327
+
328
+ .feature-list i {
329
+ color: var(--success);
330
+ }
331
+
332
+ footer {
333
+ text-align: center;
334
+ margin-top: 3rem;
335
+ padding: 1.5rem 0;
336
+ color: var(--secondary);
337
+ font-size: 0.875rem;
338
+ border-top: 1px solid #e2e8f0;
339
+ }
340
+
341
+ .notification {
342
+ position: fixed;
343
+ bottom: 20px;
344
+ right: 20px;
345
+ padding: 1rem 1.5rem;
346
+ background: var(--success);
347
+ color: white;
348
+ border-radius: 0.5rem;
349
+ box-shadow: var(--shadow);
350
+ display: none;
351
+ z-index: 1000;
352
+ }
353
+
354
+ /* New Styles for Guide Section */
355
+ .guide-section {
356
+ background: white;
357
+ border-radius: 1rem;
358
+ padding: 2rem;
359
+ box-shadow: var(--shadow);
360
+ margin-top: 2rem;
361
+ }
362
+
363
+ .guide-header {
364
+ display: flex;
365
+ justify-content: space-between;
366
+ align-items: center;
367
+ margin-bottom: 1.5rem;
368
+ }
369
+
370
+ .guide-toggle {
371
+ background: var(--primary);
372
+ color: white;
373
+ border: none;
374
+ padding: 0.5rem 1rem;
375
+ border-radius: 0.5rem;
376
+ cursor: pointer;
377
+ transition: background 0.3s;
378
+ display: flex;
379
+ align-items: center;
380
+ gap: 0.5rem;
381
+ }
382
+
383
+ .guide-toggle:hover {
384
+ background: var(--primary-dark);
385
+ }
386
+
387
+ .guide-content {
388
+ display: none;
389
+ grid-template-columns: repeat(auto-fit, minmax(300px, 1fr));
390
+ gap: 1.5rem;
391
+ }
392
+
393
+ .guide-step {
394
+ display: flex;
395
+ flex-direction: column;
396
+ gap: 0.75rem;
397
+ }
398
+
399
+ .step-number {
400
+ display: inline-flex;
401
+ align-items: center;
402
+ justify-content: center;
403
+ width: 30px;
404
+ height: 30px;
405
+ background: var(--primary);
406
+ color: white;
407
+ border-radius: 50%;
408
+ font-weight: 600;
409
+ margin-right: 0.5rem;
410
+ }
411
+
412
+ .step-title {
413
+ font-weight: 600;
414
+ color: var(--primary);
415
+ margin-bottom: 0.5rem;
416
+ }
417
+
418
+ .step-icon {
419
+ font-size: 1.5rem;
420
+ color: var(--primary);
421
+ margin-bottom: 0.5rem;
422
+ }
423
+
424
+ .guide-tips {
425
+ background: #f0f9ff;
426
+ border-radius: 0.75rem;
427
+ padding: 1.5rem;
428
+ margin-top: 1.5rem;
429
+ }
430
+
431
+ .tips-title {
432
+ font-weight: 600;
433
+ color: var(--primary);
434
+ margin-bottom: 1rem;
435
+ }
436
+
437
+ .tips-list {
438
+ list-style: none;
439
+ }
440
+
441
+ .tips-list li {
442
+ padding: 0.5rem 0;
443
+ display: flex;
444
+ align-items: flex-start;
445
+ gap: 0.75rem;
446
+ }
447
+
448
+ .tips-list i {
449
+ color: var(--accent);
450
+ margin-top: 0.25rem;
451
+ }
452
+
453
+ .guide-open {
454
+ display: grid;
455
+ }
456
+ </style>
457
+ </head>
458
+
459
+ <body>
460
+ <div class="container">
461
+ <header>
462
+ <div class="logo">
463
+ <i class="fas fa-camera-retro"></i>
464
+ <span>Professional Portrait Creator</span>
465
+ </div>
466
+ <div class="built-with">
467
+ Built with <a href="https://huggingface.co/spaces/akhaliq/anycoder" target="_blank">anycoder</a>
468
+ </div>
469
+ </header>
470
+
471
+ <main>
472
+ <div class="card">
473
+ <h2 class="card-title"><i class="fas fa-upload"></i> Upload Your Photo</h2>
474
+ <div class="upload-area" id="uploadArea">
475
+ <i class="fas fa-cloud-upload-alt upload-icon"></i>
476
+ <p class="upload-text">Drag & drop your iPhone photo here</p>
477
+ <p class="upload-text">or</p>
478
+ <button class="upload-button" id="uploadButton">
479
+ <i class="fas fa-folder-open"></i> Browse Files
480
+ </button>
481
+ <input type="file" id="fileInput" accept="image/*" style="display: none;">
482
+ </div>
483
+
484
+ <div class="preview-container" id="previewContainer">
485
+ <p class="preview-title">Photo Preview:</p>
486
+ <img id="previewImage" class="preview-image" src="" alt="Preview">
487
+ </div>
488
+
489
+ <div class="options">
490
+ <div class="option-group">
491
+ <label class="option-label">Background Blur (Bokeh)</label>
492
+ <div class="slider-container">
493
+ <input type="range" min="1" max="10" value="7" class="slider" id="blurSlider">
494
+ <span class="slider-value" id="blurValue">7</span>
495
+ </div>
496
+ </div>
497
+
498
+ <div class="option-group">
499
+ <label class="option-label">Professional Enhancement</label>
500
+ <div class="slider-container">
501
+ <input type="range" min="1" max="10" value="8" class="slider" id="enhanceSlider">
502
+ <span class="slider-value" id="enhanceValue">8</span>
503
+ </div>
504
+ </div>
505
+
506
+ <div class="option-group">
507
+ <label class="option-label">Background Style</label>
508
+ <select id="backgroundStyle" class="slider" style="width: 100%; padding: 0.5rem; border-radius: 0.5rem; border: 1px solid #cbd5e1;">
509
+ <option value="modern">Modern Office</option>
510
+ <option value="corporate">Corporate Environment</option>
511
+ <option value="executive">Executive Suite</option>
512
+ </select>
513
+ </div>
514
+ </div>
515
+
516
+ <div class="button-group">
517
+ <button class="btn btn-primary" id="generateBtn">
518
+ <i class="fas fa-magic"></i> Generate Portrait
519
+ </button>
520
+ <button class="btn btn-secondary" id="resetBtn">
521
+ <i class="fas fa-redo"></i> Reset
522
+ </button>
523
+ </div>
524
+ </div>
525
+
526
+ <div class="card">
527
+ <h2 class="card-title"><i class="fas fa-image"></i> Your Professional Portrait</h2>
528
+
529
+ <div class="loading" id="loading">
530
+ <div class="loading-spinner"></div>
531
+ <p>Creating your professional portrait with Qwen Image Edit 2509...</p>
532
+ </div>
533
+
534
+ <div class="result-container" id="resultContainer">
535
+ <h3 class="result-title">Your Enhanced Business Portrait</h3>
536
+ <img id="resultImage" class="result-image" src="" alt="Enhanced Portrait">
537
+ <div class="button-group">
538
+ <button class="btn btn-primary" id="downloadBtn">
539
+ <i class="fas fa-download"></i> Download Portrait
540
+ </button>
541
+ </div>
542
+ </div>
543
+
544
+ <div id="placeholderResult">
545
+ <p style="text-align: center; color: var(--secondary); padding: 4rem 2rem;">
546
+ <i class="fas fa-user-tie" style="font-size: 4rem; margin-bottom: 1rem; color: #e2e8f0;"></i><br>
547
+ Your enhanced business portrait will appear here after processing.
548
+ </p>
549
+
550
+ <h3 class="card-title" style="margin-top: 2rem;"><i class="fas fa-star"></i> Features</h3>
551
+ <ul class="feature-list">
552
+ <li><i class="fas fa-check-circle"></i> High-quality portrait enhancement</li>
553
+ <li><i class="fas fa-check-circle"></i> Professional bokeh office background</li>
554
+ <li><i class="fas fa-check-circle"></i> Lighting and color correction</li>
555
+ <li><i class="fas fa-check-circle"></i> Professional attire enhancement</li>
556
+ <li><i class="fas fa-check-circle"></i> Optimized for LinkedIn & professional profiles</li>
557
+ </ul>
558
+ </div>
559
+ </div>
560
+ </main>
561
+
562
+ <!-- New How to Run Guide Section -->
563
+ <section class="guide-section">
564
+ <div class="guide-header">
565
+ <h2 class="card-title"><i class="fas fa-question-circle"></i> How to Use This Application</h2>
566
+ <button class="guide-toggle" id="guideToggle">
567
+ <i class="fas fa-chevron-down"></i> Show Instructions
568
+ </button>
569
+ </div>
570
+
571
+ <div class="guide-content" id="guideContent">
572
+ <div class="guide-step">
573
+ <div class="step-title">
574
+ <span class="step-number">1</span> Upload Your Photo
575
+ </div>
576
+ <p>Click "Browse Files" or drag and drop your photo directly into the upload area. Supported formats include JPG, PNG, and WebP.</p>
577
+ </div>
578
+
579
+ <div class="guide-step">
580
+ <div class="step-title">
581
+ <span class="step-number">2</span> Adjust Settings
582
+ </div>
583
+ <p>Customize your portrait using the sliders and dropdown menu. You can control the background blur, enhancement level, and background style.</p>
584
+ </div>
585
+
586
+ <div class="guide-step">
587
+ <div class="step-title">
588
+ <span class="step-number">3</span> Generate Portrait
589
+ </div>
590
+ <p>Click "Generate Portrait" to process your image. The system will create a professional business portrait with your selected settings.</p>
591
+ </div>
592
+
593
+ <div class="guide-step">
594
+ <div class="step-title">
595
+ <span class="step-number">4</span> Download Result
596
+ </div>
597
+ <p>Once processing is complete, click "Download Portrait" to save your enhanced professional image.</p>
598
+ </div>
599
+
600
+ <div class="guide-tips">
601
+ <h3 class="tips-title"><i class="fas fa-lightbulb"></i> Pro Tips</h3>
602
+ <ul class="tips-list">
603
+ <li><i class="fas fa-camera"></i> Use a clear, well-lit photo for best results</li>
604
+ <li><i class="fas fa-user"></i> For portraits, ensure your face is clearly visible</li>
605
+ <li><i class="fas fa-sun"></i> Medium enhancement levels (6-8) typically work best</li>
606
+ <li><i class="fas fa-download"></i> Downloaded images are high-resolution PNG files</li>
607
+ </ul>
608
+ </div>
609
+ </div>
610
+ </section>
611
+
612
+ <footer>
613
+ <p>Professional Portrait Creator &copy; 2023 | Powered by Qwen Image Edit 2509</p>
614
+ </footer>
615
+ </div>
616
+
617
+ <div class="notification" id="notification">
618
+ <i class="fas fa-check-circle"></i> Portrait successfully generated!
619
+ </div>
620
+
621
+ <script>
622
+ // DOM Elements
623
+ const uploadArea = document.getElementById('uploadArea');
624
+ const uploadButton = document.getElementById('uploadButton');
625
+ const fileInput = document.getElementById('fileInput');
626
+ const previewContainer = document.getElementById('previewContainer');
627
+ const previewImage = document.getElementById('previewImage');
628
+ const blurSlider = document.getElementById('blurSlider');
629
+ const blurValue = document.getElementById('blurValue');
630
+ const enhanceSlider = document.getElementById('enhanceSlider');
631
+ const enhanceValue = document.getElementById('enhanceValue');
632
+ const generateBtn = document.getElementById('generateBtn');
633
+ const resetBtn = document.getElementById('resetBtn');
634
+ const loading = document.getElementById('loading');
635
+ const resultContainer = document.getElementById('resultContainer');
636
+ const placeholderResult = document.getElementById('placeholderResult');
637
+ const resultImage = document.getElementById('resultImage');
638
+ const downloadBtn = document.getElementById('downloadBtn');
639
+ const notification = document.getElementById('notification');
640
+
641
+ // New guide elements
642
+ const guideToggle = document.getElementById('guideToggle');
643
+ const guideContent = document.getElementById('guideContent');
644
+
645
+ // Event Listeners
646
+ uploadButton.addEventListener('click', () => {
647
+ fileInput.click();
648
+ });
649
+
650
+ uploadArea.addEventListener('dragover', (e) => {
651
+ e.preventDefault();
652
+ uploadArea.classList.add('active');
653
+ });
654
+
655
+ uploadArea.addEventListener('dragleave', () => {
656
+ uploadArea.classList.remove('active');
657
+ });
658
+
659
+ uploadArea.addEventListener('drop', (e) => {
660
+ e.preventDefault();
661
+ uploadArea.classList.remove('active');
662
+
663
+ if (e.dataTransfer.files.length) {
664
+ handleFile(e.dataTransfer.files[0]);
665
+ }
666
+ });
667
+
668
+ fileInput.addEventListener('change', (e) => {
669
+ if (e.target.files.length) {
670
+ handleFile(e.target.files[0]);
671
+ }
672
+ });
673
+
674
+ blurSlider.addEventListener('input', () => {
675
+ blurValue.textContent = blurSlider.value;
676
+ });
677
+
678
+ enhanceSlider.addEventListener('input', () => {
679
+ enhanceValue.textContent = enhanceSlider.value;
680
+ });
681
+
682
+ generateBtn.addEventListener('click', generatePortrait);
683
+ resetBtn.addEventListener('click', resetForm);
684
+ downloadBtn.addEventListener('click', downloadPortrait);
685
+
686
+ // Guide toggle functionality
687
+ guideToggle.addEventListener('click', () => {
688
+ guideContent.classList.toggle('guide-open');
689
+
690
+ if (guideContent.classList.contains('guide-open')) {
691
+ guideToggle.innerHTML = '<i class="fas fa-chevron-up"></i> Hide Instructions';
692
+ } else {
693
+ guideToggle.innerHTML = '<i class="fas fa-chevron-down"></i> Show Instructions';
694
+ }
695
+ });
696
+
697
+ // Functions
698
+ function handleFile(file) {
699
+ if (!file.type.match('image.*')) {
700
+ alert('Please select an image file.');
701
+ return;
702
+ }
703
+
704
+ const reader = new FileReader();
705
+
706
+ reader.onload = (e) => {
707
+ previewImage.src = e.target.result;
708
+ previewContainer.style.display = 'block';
709
+ generateBtn.disabled = false;
710
+ };
711
+
712
+ reader.readAsDataURL(file);
713
+ }
714
+
715
+ function generatePortrait() {
716
+ if (!previewImage.src) {
717
+ alert('Please upload a photo first.');
718
+ return;
719
+ }
720
+
721
+ // Show loading state
722
+ loading.style.display = 'block';
723
+ placeholderResult.style.display = 'none';
724
+ resultContainer.style.display = 'none';
725
+ generateBtn.disabled = true;
726
+
727
+ // Simulate processing time (in a real app, this would call an API)
728
+ setTimeout(() => {
729
+ loading.style.display = 'none';
730
+ resultContainer.style.display = 'block';
731
+
732
+ // In a real implementation, this would be the result from Qwen Image Edit 2509
733
+ // For demo purposes, we'll use the same image with a filter applied
734
+ applyImageFilter();
735
+
736
+ // Show notification
737
+ notification.style.display = 'block';
738
+ setTimeout(() => {
739
+ notification.style.display = 'none';
740
+ }, 3000);
741
+ }, 3000);
742
+ }
743
+
744
+ function applyImageFilter() {
745
+ // Create a canvas to apply filter effects
746
+ const canvas = document.createElement('canvas');
747
+ const ctx = canvas.getContext('2d');
748
+ const img = new Image();
749
+
750
+ img.onload = function() {
751
+ canvas.width = img.width;
752
+ canvas.height = img.height;
753
+
754
+ // Draw original image
755
+ ctx.drawImage(img, 0, 0);
756
+
757
+ // Apply a simple filter for demo (in real app, this would be Qwen processing)
758
+ const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
759
+ const data = imageData.data;
760
+
761
+ // Enhance contrast and saturation slightly
762
+ for (let i = 0; i < data.length; i += 4) {
763
+ // Increase contrast
764
+ data[i] = data[i] < 128 ? data[i] * 0.9 : 255 - (255 - data[i]) * 0.9; // Red
765
+ data[i + 1] = data[i + 1] < 128 ? data[i + 1] * 0.9 : 255 - (255 - data[i + 1]) * 0.9; // Green
766
+ data[i + 2] = data[i + 2] < 128 ? data[i + 2] * 0.9 : 255 - (255 - data[i + 2]) * 0.9; // Blue
767
+ }
768
+
769
+ ctx.putImageData(imageData, 0, 0);
770
+
771
+ // Set the result image
772
+ resultImage.src = canvas.toDataURL();
773
+ };
774
+
775
+ img.src = previewImage.src;
776
+ }
777
+
778
+ function resetForm() {
779
+ fileInput.value = '';
780
+ previewImage.src = '';
781
+ previewContainer.style.display = 'none';
782
+ resultContainer.style.display = 'none';
783
+ placeholderResult.style.display = 'block';
784
+ generateBtn.disabled = true;
785
+ blurSlider.value = 7;
786
+ blurValue.textContent = 7;
787
+ enhanceSlider.value = 8;
788
+ enhanceValue.textContent = 8;
789
+ }
790
+
791
+ function downloadPortrait() {
792
+ if (!resultImage.src) return;
793
+
794
+ const link = document.createElement('a');
795
+ link.download = 'professional-portrait.png';
796
+ link.href = resultImage.src;
797
+ link.click();
798
+ }
799
+
800
+ // Initialize
801
+ resetForm();
802
+ </script>
803
+ </body>
804
+
805
+ </html>