Files changed (1) hide show
  1. app.py +0 -465
app.py DELETED
@@ -1,465 +0,0 @@
1
- import gradio as gr
2
- import torch
3
- import torch.nn as nn
4
- from torchvision import transforms
5
- from PIL import Image
6
- import numpy as np
7
-
8
- # =========================================================
9
- # DEVICE
10
- # =========================================================
11
- device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
12
-
13
- # =========================================================
14
- # MODEL ARCHITECTURE
15
- # =========================================================
16
- class UNetDown(nn.Module):
17
-
18
- def __init__(
19
- self,
20
- in_channels,
21
- out_channels,
22
- normalize=True,
23
- dropout=0.0
24
- ):
25
-
26
- super().__init__()
27
-
28
- layers = [
29
- nn.Conv2d(
30
- in_channels,
31
- out_channels,
32
- 4,
33
- 2,
34
- 1,
35
- bias=False
36
- )
37
- ]
38
-
39
- if normalize:
40
- layers.append(
41
- nn.InstanceNorm2d(out_channels)
42
- )
43
-
44
- layers.append(
45
- nn.LeakyReLU(0.2)
46
- )
47
-
48
- if dropout:
49
- layers.append(
50
- nn.Dropout(dropout)
51
- )
52
-
53
- self.model = nn.Sequential(*layers)
54
-
55
- def forward(self, x):
56
-
57
- return self.model(x)
58
-
59
- class UNetUp(nn.Module):
60
-
61
- def __init__(
62
- self,
63
- in_channels,
64
- out_channels,
65
- dropout=0.0
66
- ):
67
-
68
- super().__init__()
69
-
70
- layers = [
71
-
72
- nn.ConvTranspose2d(
73
- in_channels,
74
- out_channels,
75
- 4,
76
- 2,
77
- 1,
78
- bias=False
79
- ),
80
-
81
- nn.InstanceNorm2d(out_channels),
82
-
83
- nn.ReLU(inplace=True)
84
- ]
85
-
86
- if dropout:
87
- layers.append(
88
- nn.Dropout(dropout)
89
- )
90
-
91
- self.model = nn.Sequential(*layers)
92
-
93
- def forward(self, x, skip_input):
94
-
95
- x = self.model(x)
96
-
97
- x = torch.cat((x, skip_input), 1)
98
-
99
- return x
100
-
101
- class Generator(nn.Module):
102
-
103
- def __init__(
104
- self,
105
- in_channels=3,
106
- out_channels=3
107
- ):
108
-
109
- super().__init__()
110
-
111
- self.down1 = UNetDown(in_channels, 64, normalize=False)
112
-
113
- self.down2 = UNetDown(64, 128)
114
-
115
- self.down3 = UNetDown(128, 256)
116
-
117
- self.down4 = UNetDown(256, 512, dropout=0.5)
118
-
119
- self.down5 = UNetDown(512, 512, dropout=0.5)
120
-
121
- self.down6 = UNetDown(512, 512, dropout=0.5)
122
-
123
- self.down7 = UNetDown(
124
- 512,
125
- 512,
126
- normalize=False,
127
- dropout=0.5
128
- )
129
-
130
- self.up1 = UNetUp(512, 512, dropout=0.5)
131
-
132
- self.up2 = UNetUp(1024, 512, dropout=0.5)
133
-
134
- self.up3 = UNetUp(1024, 512, dropout=0.5)
135
-
136
- self.up4 = UNetUp(1024, 256)
137
-
138
- self.up5 = UNetUp(512, 128)
139
-
140
- self.up6 = UNetUp(256, 64)
141
-
142
- self.final = nn.Sequential(
143
-
144
- nn.ConvTranspose2d(
145
- 128,
146
- out_channels,
147
- 4,
148
- 2,
149
- 1
150
- ),
151
-
152
- nn.Tanh()
153
- )
154
-
155
- def forward(self, x):
156
-
157
- d1 = self.down1(x)
158
-
159
- d2 = self.down2(d1)
160
-
161
- d3 = self.down3(d2)
162
-
163
- d4 = self.down4(d3)
164
-
165
- d5 = self.down5(d4)
166
-
167
- d6 = self.down6(d5)
168
-
169
- d7 = self.down7(d6)
170
-
171
- u1 = self.up1(d7, d6)
172
-
173
- u2 = self.up2(u1, d5)
174
-
175
- u3 = self.up3(u2, d4)
176
-
177
- u4 = self.up4(u3, d3)
178
-
179
- u5 = self.up5(u4, d2)
180
-
181
- u6 = self.up6(u5, d1)
182
-
183
- return self.final(u6)
184
-
185
- # =========================================================
186
- # LOAD MODEL
187
- # =========================================================
188
- generator = Generator().to(device)
189
-
190
- generator.load_state_dict(
191
- torch.load(
192
- "generator_model.pth",
193
- map_location=device
194
- )
195
- )
196
-
197
- generator.eval()
198
-
199
- # =========================================================
200
- # STYLE TRANSFER FUNCTION
201
- # =========================================================
202
- def monet_style_transfer(
203
- input_image,
204
- style_strength,
205
- image_quality
206
- ):
207
-
208
- if input_image is None:
209
-
210
- return None, "⚠️ Please upload an image."
211
-
212
- transform = transforms.Compose([
213
-
214
- transforms.Resize((256, 256)),
215
-
216
- transforms.ToTensor(),
217
-
218
- transforms.Normalize(
219
- (0.5, 0.5, 0.5),
220
- (0.5, 0.5, 0.5)
221
- )
222
- ])
223
-
224
- input_image = input_image.convert("RGB")
225
-
226
- img_tensor = transform(input_image).unsqueeze(0).to(device)
227
-
228
- with torch.no_grad():
229
-
230
- styled = generator(img_tensor)
231
-
232
- # =====================================================
233
- # STYLE STRENGTH CONTROL
234
- # =====================================================
235
- styled = styled * (style_strength / 100)
236
-
237
- styled = styled * 0.5 + 0.5
238
-
239
- styled = styled.squeeze(0).cpu().permute(1, 2, 0).numpy()
240
-
241
- styled = (styled * 255).clip(0, 255).astype("uint8")
242
-
243
- output_image = Image.fromarray(styled)
244
-
245
- result_text = f"""
246
- # 🎨 Monet Style Transformation Complete
247
-
248
- ### Style Strength: {style_strength}%
249
-
250
- ### Image Quality: {image_quality}
251
-
252
- ### AI artistic rendering successfully generated.
253
- """
254
-
255
- return output_image, result_text
256
-
257
- # =========================================================
258
- # CUSTOM CSS
259
- # =========================================================
260
- custom_css = """
261
- body {
262
- background: #f5f7fb;
263
- font-family: 'Segoe UI', sans-serif;
264
- }
265
-
266
- .gradio-container {
267
- max-width: 1300px !important;
268
- margin: auto;
269
- }
270
-
271
- .hero {
272
- background: linear-gradient(135deg,#111827,#7c3aed);
273
- padding: 40px;
274
- border-radius: 30px;
275
- color: white;
276
- margin-bottom: 20px;
277
- }
278
-
279
- .hero h1 {
280
- font-size: 52px;
281
- font-weight: 800;
282
- margin-bottom: 10px;
283
- }
284
-
285
- .hero p {
286
- font-size: 18px;
287
- opacity: 0.92;
288
- }
289
-
290
- .card {
291
- background: white;
292
- border-radius: 24px;
293
- padding: 22px;
294
- box-shadow: 0 6px 18px rgba(0,0,0,0.08);
295
- }
296
-
297
- button {
298
- height: 60px !important;
299
- border-radius: 18px !important;
300
- border: none !important;
301
- background: linear-gradient(135deg,#7c3aed,#6d28d9) !important;
302
- color: white !important;
303
- font-size: 20px !important;
304
- font-weight: 700 !important;
305
- }
306
-
307
- button:hover {
308
- background: linear-gradient(135deg,#6d28d9,#5b21b6) !important;
309
- }
310
-
311
- input, textarea, select {
312
- border-radius: 16px !important;
313
- }
314
-
315
- @media (max-width: 768px){
316
-
317
- .hero {
318
- padding: 22px;
319
- }
320
-
321
- .hero h1 {
322
- font-size: 32px;
323
- }
324
-
325
- .hero p {
326
- font-size: 15px;
327
- }
328
-
329
- button {
330
- height: 54px !important;
331
- font-size: 17px !important;
332
- }
333
- }
334
- """
335
-
336
- # =========================================================
337
- # HERO HTML
338
- # =========================================================
339
- hero_html = """
340
- <div class="hero">
341
-
342
- <h1>🎨 AI Monet Style Transfer</h1>
343
-
344
- <p>
345
- Transform your photos into Monet-inspired paintings using deep learning.
346
- Modern mobile-friendly interface with smart controls and AI-powered rendering.
347
- </p>
348
-
349
- </div>
350
- """
351
-
352
- # =========================================================
353
- # INTERFACE
354
- # =========================================================
355
- with gr.Blocks(
356
- css=custom_css,
357
- theme=gr.themes.Soft(
358
- primary_hue="violet",
359
- secondary_hue="purple"
360
- )
361
- ) as demo:
362
-
363
- gr.HTML(hero_html)
364
-
365
- # =====================================================
366
- # TOP INFO CARDS
367
- # =====================================================
368
- with gr.Row():
369
-
370
- with gr.Column():
371
- gr.Markdown("""
372
- ### ⚡ Fast AI Rendering
373
- Generate artistic images instantly
374
- """)
375
-
376
- with gr.Column():
377
- gr.Markdown("""
378
- ### 📱 Mobile Responsive
379
- Optimized for all screen sizes
380
- """)
381
-
382
- with gr.Column():
383
- gr.Markdown("""
384
- ### 🧠 Deep Learning
385
- GAN-based artistic transformation
386
- """)
387
-
388
- # =====================================================
389
- # MAIN AREA
390
- # =====================================================
391
- with gr.Row():
392
-
393
- # =================================================
394
- # LEFT PANEL
395
- # =================================================
396
- with gr.Column(scale=1):
397
-
398
- input_image = gr.Image(
399
- type="pil",
400
- label="🖼️ Upload Photo"
401
- )
402
-
403
- style_strength = gr.Slider(
404
- minimum=10,
405
- maximum=100,
406
- value=80,
407
- step=5,
408
- label="🎨 Style Strength"
409
- )
410
-
411
- image_quality = gr.Dropdown(
412
- choices=[
413
- "Standard",
414
- "High",
415
- "Ultra"
416
- ],
417
- value="High",
418
- label="✨ Image Quality"
419
- )
420
-
421
- transform_button = gr.Button(
422
- "🚀 Generate Monet Art",
423
- variant="primary"
424
- )
425
-
426
- # =================================================
427
- # RIGHT PANEL
428
- # =================================================
429
- with gr.Column(scale=1):
430
-
431
- output_image = gr.Image(
432
- type="pil",
433
- label="🖌️ Monet Styled Image"
434
- )
435
-
436
- result_text = gr.Markdown()
437
-
438
- # =====================================================
439
- # EXAMPLES
440
- # =====================================================
441
- gr.Examples(
442
- examples=[],
443
- inputs=[input_image]
444
- )
445
-
446
- # =====================================================
447
- # BUTTON ACTION
448
- # =====================================================
449
- transform_button.click(
450
- fn=monet_style_transfer,
451
- inputs=[
452
- input_image,
453
- style_strength,
454
- image_quality
455
- ],
456
- outputs=[
457
- output_image,
458
- result_text
459
- ]
460
- )
461
-
462
- # =========================================================
463
- # LAUNCH
464
- # =========================================================
465
- demo.launch()