nftnik commited on
Commit
f8708de
·
verified ·
1 Parent(s): 8f8e7eb

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +275 -255
app.py CHANGED
@@ -34,10 +34,10 @@ folder_paths.set_output_directory(output_dir)
34
  # Configurar caminhos dos modelos e verificar estrutura
35
  MODEL_FOLDERS = ["style_models", "text_encoders", "vae", "unet", "clip_vision"]
36
  for model_folder in MODEL_FOLDERS:
37
- folder_path = os.path.join(models_dir, model_folder)
38
- os.makedirs(folder_path, exist_ok=True)
39
- folder_paths.add_model_folder_path(model_folder, folder_path)
40
- logger.info(f"Pasta de modelo configurada: {model_folder}")
41
 
42
  # 4. Diagnóstico CUDA
43
  logger.info(f"Python version: {sys.version}")
@@ -45,301 +45,321 @@ logger.info(f"Torch version: {torch.__version__}")
45
  logger.info(f"CUDA disponível: {torch.cuda.is_available()}")
46
  logger.info(f"Quantidade de GPUs: {torch.cuda.device_count()}")
47
  if torch.cuda.is_available():
48
- logger.info(f"GPU atual: {torch.cuda.get_device_name(0)}")
49
 
50
  # 5. Inicialização do ComfyUI
51
  logger.info("Inicializando ComfyUI...")
52
  try:
53
- init_extra_nodes()
54
  except Exception as e:
55
- logger.warning(f"Aviso na inicialização de nós extras: {str(e)}")
56
- logger.info("Continuando mesmo com avisos nos nós extras...")
57
 
58
  # 6. Helper Functions
59
  def get_value_at_index(obj: Union[Sequence, Mapping], index: int) -> Any:
60
- try:
61
- return obj[index]
62
- except KeyError:
63
- return obj["result"][index]
64
 
65
  def verify_file_exists(folder: str, filename: str) -> bool:
66
- file_path = os.path.join(models_dir, folder, filename)
67
- exists = os.path.exists(file_path)
68
- if not exists:
69
- logger.error(f"Arquivo não encontrado: {file_path}")
70
- return exists
71
 
72
  # 7. Download de Modelos
73
  logger.info("Baixando modelos necessários...")
74
  try:
75
- hf_hub_download(repo_id="black-forest-labs/FLUX.1-Redux-dev",
76
- filename="flux1-redux-dev.safetensors",
77
- local_dir=os.path.join(models_dir, "style_models"))
78
- hf_hub_download(repo_id="comfyanonymous/flux_text_encoders",
79
- filename="t5xxl_fp16.safetensors",
80
- local_dir=os.path.join(models_dir, "text_encoders"))
81
- hf_hub_download(repo_id="zer0int/CLIP-GmP-ViT-L-14",
82
- filename="ViT-L-14-TEXT-detail-improved-hiT-GmP-TE-only-HF.safetensors",
83
- local_dir=os.path.join(models_dir, "text_encoders"))
84
- hf_hub_download(repo_id="black-forest-labs/FLUX.1-dev",
85
- filename="ae.safetensors",
86
- local_dir=os.path.join(models_dir, "vae"))
87
- hf_hub_download(repo_id="black-forest-labs/FLUX.1-dev",
88
- filename="flux1-dev.safetensors",
89
- local_dir=os.path.join(models_dir, "unet"))
90
- hf_hub_download(repo_id="Comfy-Org/sigclip_vision_384",
91
- filename="sigclip_vision_patch14_384.safetensors",
92
- local_dir=os.path.join(models_dir, "clip_vision"))
 
 
 
 
 
 
 
 
 
 
 
 
93
  except Exception as e:
94
- logger.error(f"Erro ao baixar modelos: {str(e)}")
95
- raise
96
 
97
  # 8. Inicialização dos Modelos
98
  logger.info("Inicializando modelos...")
99
  try:
100
- with torch.inference_mode():
101
- # CLIP
102
- logger.info("Carregando CLIP...")
103
- dualcliploader = NODE_CLASS_MAPPINGS["DualCLIPLoader"]()
104
- CLIP_MODEL = dualcliploader.load_clip(
105
- clip_name1="t5xxl_fp16.safetensors",
106
- clip_name2="ViT-L-14-TEXT-detail-improved-hiT-GmP-TE-only-HF.safetensors",
107
- type="flux"
108
- )
109
- if CLIP_MODEL is None:
110
- raise ValueError("Falha ao carregar CLIP model")
 
 
111
 
112
- # CLIP Vision
113
- logger.info("Carregando CLIP Vision...")
114
- clipvisionloader = NODE_CLASS_MAPPINGS["CLIPVisionLoader"]()
115
- CLIP_VISION = clipvisionloader.load_clip(
116
- clip_name="sigclip_vision_patch14_384.safetensors"
117
- )
118
- if CLIP_VISION is None:
119
- raise ValueError("Falha ao carregar CLIP Vision model")
120
 
121
- # Style Model (Carregado separadamente)
122
- logger.info("Carregando Style Model...")
123
- stylemodelloader = NODE_CLASS_MAPPINGS["StyleModelLoader"]()
124
- STYLE_MODEL = stylemodelloader.load_style_model(
125
- style_model_name="flux1-redux-dev.safetensors"
126
- )
127
- if STYLE_MODEL is None:
128
- raise ValueError("Falha ao carregar Style Model")
129
 
130
- # VAE
131
- logger.info("Carregando VAE...")
132
- vaeloader = NODE_CLASS_MAPPINGS["VAELoader"]()
133
- VAE_MODEL = vaeloader.load_vae(
134
- vae_name="ae.safetensors"
135
- )
136
- if VAE_MODEL is None:
137
- raise ValueError("Falha ao carregar VAE model")
138
 
139
- # UNET
140
- logger.info("Carregando UNET...")
141
- unetloader = NODE_CLASS_MAPPINGS["UNETLoader"]()
142
- UNET_MODEL = unetloader.load_unet(
143
- unet_name="flux1-dev.safetensors",
144
- weight_dtype="fp8_e4m3fn"
145
- )
146
- if UNET_MODEL is None:
147
- raise ValueError("Falha ao carregar UNET model")
148
 
149
- logger.info("Carregando modelos na GPU...")
150
- model_loaders = [CLIP_MODEL, VAE_MODEL, CLIP_VISION, UNET_MODEL]
151
- model_management.load_models_gpu([
152
- loader[0].patcher if hasattr(loader[0], 'patcher') else loader[0]
153
- for loader in model_loaders
154
- ])
155
- logger.info("Modelos carregados com sucesso")
156
  except Exception as e:
157
- logger.error(f"Erro ao inicializar modelos: {str(e)}")
158
- raise
159
 
160
  # 9. Função de Geração
161
  @spaces.GPU
162
- def generate_image(prompt, input_image, lora_weight, guidance, downsampling_factor, weight, seed, width, height, batch_size, steps, progress=gr.Progress(track_tqdm=True)):
163
- try:
164
- with torch.no_grad():
165
- logger.info(f"Iniciando geração com prompt: {prompt}")
 
 
 
 
 
166
 
167
- # Codificar texto
168
- cliptextencode = NODE_CLASS_MAPPINGS["CLIPTextEncode"]()
169
- encoded_text = cliptextencode.encode(
170
- text=prompt,
171
- clip=CLIP_MODEL[0]
172
- )
173
 
174
- # Carregar e processar imagem
175
- loadimage = NODE_CLASS_MAPPINGS["LoadImage"]()
176
- loaded_image = loadimage.load_image(image=input_image)
177
- if loaded_image is None:
178
- raise ValueError("Erro ao carregar a imagem de entrada")
179
- logger.info("Imagem carregada com sucesso")
180
 
181
- # Flux Guidance
182
- fluxguidance = NODE_CLASS_MAPPINGS["FluxGuidance"]()
183
- flux_guidance = fluxguidance.append(
184
- guidance=guidance,
185
- conditioning=encoded_text[0]
186
- )
187
 
188
- # Redux Advanced
189
- reduxadvanced = NODE_CLASS_MAPPINGS["ReduxAdvanced"]()
190
- redux_result = reduxadvanced.apply_stylemodel(
191
- downsampling_factor=downsampling_factor,
192
- downsampling_function="area",
193
- mode="keep aspect ratio",
194
- weight=weight,
195
- conditioning=flux_guidance[0],
196
- style_model=STYLE_MODEL[0],
197
- clip_vision=CLIP_VISION[0],
198
- image=loaded_image[0]
199
- )
200
 
201
- # Empty Latent
202
- emptylatentimage = NODE_CLASS_MAPPINGS["EmptyLatentImage"]()
203
- empty_latent = emptylatentimage.generate(
204
- width=width,
205
- height=height,
206
- batch_size=batch_size
207
- )
208
 
209
- # KSampler
210
- logger.info("Iniciando sampling...")
211
- ksampler = NODE_CLASS_MAPPINGS["KSampler"]()
212
- sampled = ksampler.sample(
213
- seed=seed,
214
- steps=steps,
215
- cfg=1,
216
- sampler_name="euler",
217
- scheduler="simple",
218
- denoise=1,
219
- model=UNET_MODEL[0],
220
- positive=redux_result[0],
221
- negative=flux_guidance[0],
222
- latent_image=empty_latent[0]
223
- )
224
 
225
- # VAE Decode
226
- logger.info("Decodificando imagem...")
227
- vaedecode = NODE_CLASS_MAPPINGS["VAEDecode"]()
228
- decoded = vaedecode.decode(
229
- samples=sampled[0],
230
- vae=VAE_MODEL[0]
231
- )
232
 
233
- # Salvar imagem
234
- temp_filename = f"Flux_{random.randint(0, 99999)}.png"
235
- temp_path = os.path.join(output_dir, temp_filename)
236
- try:
237
- Image.fromarray((decoded[0] * 255).astype("uint8")).save(temp_path)
238
- logger.info(f"Imagem salva em: {temp_path}")
239
- return temp_path
240
- except Exception as e:
241
- logger.error(f"Erro ao salvar imagem: {str(e)}")
242
- return None
243
 
244
- except Exception as e:
245
- logger.error(f"Erro ao gerar imagem: {str(e)}")
246
- return None
247
 
248
  # 10. Interface Gradio
249
  with gr.Blocks() as app:
250
- gr.Markdown("# FLUX Redux Image Generator")
251
 
252
- with gr.Row():
253
- with gr.Column():
254
- prompt_input = gr.Textbox(
255
- label="Prompt",
256
- placeholder="Enter your prompt here...",
257
- lines=5
258
- )
259
- input_image = gr.Image(
260
- label="Input Image",
261
- type="filepath"
262
- )
263
 
264
- with gr.Row():
265
- with gr.Column():
266
- lora_weight = gr.Slider(
267
- minimum=0,
268
- maximum=2,
269
- step=0.1,
270
- value=0.6,
271
- label="LoRA Weight"
272
- )
273
- guidance = gr.Slider(
274
- minimum=0,
275
- maximum=20,
276
- step=0.1,
277
- value=3.5,
278
- label="Guidance"
279
- )
280
- downsampling_factor = gr.Slider(
281
- minimum=1,
282
- maximum=8,
283
- step=1,
284
- value=3,
285
- label="Downsampling Factor"
286
- )
287
- weight = gr.Slider(
288
- minimum=0,
289
- maximum=2,
290
- step=0.1,
291
- value=1.0,
292
- label="Model Weight"
293
- )
294
- with gr.Column():
295
- seed = gr.Number(
296
- value=random.randint(1, 2**64),
297
- label="Seed",
298
- precision=0
299
- )
300
- width = gr.Number(
301
- value=1024,
302
- label="Width",
303
- precision=0
304
- )
305
- height = gr.Number(
306
- value=1024,
307
- label="Height",
308
- precision=0
309
- )
310
- batch_size = gr.Number(
311
- value=1,
312
- label="Batch Size",
313
- precision=0
314
- )
315
- steps = gr.Number(
316
- value=20,
317
- label="Steps",
318
- precision=0
319
- )
320
 
321
- generate_btn = gr.Button("Generate Image")
322
 
323
- with gr.Column():
324
- output_image = gr.Image(label="Generated Image", type="filepath")
325
 
326
- generate_btn.click(
327
- fn=generate_image,
328
- inputs=[
329
- prompt_input,
330
- input_image,
331
- lora_weight,
332
- guidance,
333
- downsampling_factor,
334
- weight,
335
- seed,
336
- width,
337
- height,
338
- batch_size,
339
- steps
340
- ],
341
- outputs=[output_image]
342
- )
343
 
344
  if __name__ == "__main__":
345
- app.launch()
 
 
34
  # Configurar caminhos dos modelos e verificar estrutura
35
  MODEL_FOLDERS = ["style_models", "text_encoders", "vae", "unet", "clip_vision"]
36
  for model_folder in MODEL_FOLDERS:
37
+ folder_path = os.path.join(models_dir, model_folder)
38
+ os.makedirs(folder_path, exist_ok=True)
39
+ folder_paths.add_model_folder_path(model_folder, folder_path)
40
+ logger.info(f"Pasta de modelo configurada: {model_folder}")
41
 
42
  # 4. Diagnóstico CUDA
43
  logger.info(f"Python version: {sys.version}")
 
45
  logger.info(f"CUDA disponível: {torch.cuda.is_available()}")
46
  logger.info(f"Quantidade de GPUs: {torch.cuda.device_count()}")
47
  if torch.cuda.is_available():
48
+ logger.info(f"GPU atual: {torch.cuda.get_device_name(0)}")
49
 
50
  # 5. Inicialização do ComfyUI
51
  logger.info("Inicializando ComfyUI...")
52
  try:
53
+ init_extra_nodes()
54
  except Exception as e:
55
+ logger.warning(f"Aviso na inicialização de nós extras: {str(e)}")
56
+ logger.info("Continuando mesmo com avisos nos nós extras...")
57
 
58
  # 6. Helper Functions
59
  def get_value_at_index(obj: Union[Sequence, Mapping], index: int) -> Any:
60
+ try:
61
+ return obj[index]
62
+ except KeyError:
63
+ return obj["result"][index]
64
 
65
  def verify_file_exists(folder: str, filename: str) -> bool:
66
+ file_path = os.path.join(models_dir, folder, filename)
67
+ exists = os.path.exists(file_path)
68
+ if not exists:
69
+ logger.error(f"Arquivo não encontrado: {file_path}")
70
+ return exists
71
 
72
  # 7. Download de Modelos
73
  logger.info("Baixando modelos necessários...")
74
  try:
75
+ hf_hub_download(
76
+ repo_id="black-forest-labs/FLUX.1-Redux-dev",
77
+ filename="flux1-redux-dev.safetensors",
78
+ local_dir=os.path.join(models_dir, "style_models")
79
+ )
80
+ hf_hub_download(
81
+ repo_id="comfyanonymous/flux_text_encoders",
82
+ filename="t5xxl_fp16.safetensors",
83
+ local_dir=os.path.join(models_dir, "text_encoders")
84
+ )
85
+ hf_hub_download(
86
+ repo_id="zer0int/CLIP-GmP-ViT-L-14",
87
+ filename="ViT-L-14-TEXT-detail-improved-hiT-GmP-TE-only-HF.safetensors",
88
+ local_dir=os.path.join(models_dir, "text_encoders")
89
+ )
90
+ hf_hub_download(
91
+ repo_id="black-forest-labs/FLUX.1-dev",
92
+ filename="ae.safetensors",
93
+ local_dir=os.path.join(models_dir, "vae")
94
+ )
95
+ hf_hub_download(
96
+ repo_id="black-forest-labs/FLUX.1-dev",
97
+ filename="flux1-dev.safetensors",
98
+ local_dir=os.path.join(models_dir, "unet")
99
+ )
100
+ hf_hub_download(
101
+ repo_id="Comfy-Org/sigclip_vision_384",
102
+ filename="sigclip_vision_patch14_384.safetensors",
103
+ local_dir=os.path.join(models_dir, "clip_vision")
104
+ )
105
  except Exception as e:
106
+ logger.error(f"Erro ao baixar modelos: {str(e)}")
107
+ raise
108
 
109
  # 8. Inicialização dos Modelos
110
  logger.info("Inicializando modelos...")
111
  try:
112
+ # Use torch.no_grad() em vez de torch.inference_mode()
113
+ # para evitar o erro de version counter.
114
+ with torch.no_grad():
115
+ # CLIP
116
+ logger.info("Carregando CLIP...")
117
+ dualcliploader = NODE_CLASS_MAPPINGS["DualCLIPLoader"]()
118
+ CLIP_MODEL = dualcliploader.load_clip(
119
+ clip_name1="t5xxl_fp16.safetensors",
120
+ clip_name2="ViT-L-14-TEXT-detail-improved-hiT-GmP-TE-only-HF.safetensors",
121
+ type="flux"
122
+ )
123
+ if CLIP_MODEL is None:
124
+ raise ValueError("Falha ao carregar CLIP model")
125
 
126
+ # CLIP Vision
127
+ logger.info("Carregando CLIP Vision...")
128
+ clipvisionloader = NODE_CLASS_MAPPINGS["CLIPVisionLoader"]()
129
+ CLIP_VISION = clipvisionloader.load_clip(
130
+ clip_name="sigclip_vision_patch14_384.safetensors"
131
+ )
132
+ if CLIP_VISION is None:
133
+ raise ValueError("Falha ao carregar CLIP Vision model")
134
 
135
+ # Style Model
136
+ logger.info("Carregando Style Model...")
137
+ stylemodelloader = NODE_CLASS_MAPPINGS["StyleModelLoader"]()
138
+ STYLE_MODEL = stylemodelloader.load_style_model(
139
+ style_model_name="flux1-redux-dev.safetensors"
140
+ )
141
+ if STYLE_MODEL is None:
142
+ raise ValueError("Falha ao carregar Style Model")
143
 
144
+ # VAE
145
+ logger.info("Carregando VAE...")
146
+ vaeloader = NODE_CLASS_MAPPINGS["VAELoader"]()
147
+ VAE_MODEL = vaeloader.load_vae(
148
+ vae_name="ae.safetensors"
149
+ )
150
+ if VAE_MODEL is None:
151
+ raise ValueError("Falha ao carregar VAE model")
152
 
153
+ # UNET
154
+ logger.info("Carregando UNET...")
155
+ unetloader = NODE_CLASS_MAPPINGS["UNETLoader"]()
156
+ UNET_MODEL = unetloader.load_unet(
157
+ unet_name="flux1-dev.safetensors",
158
+ weight_dtype="fp8_e4m3fn" # Ajuste a seu hardware, se necessário
159
+ )
160
+ if UNET_MODEL is None:
161
+ raise ValueError("Falha ao carregar UNET model")
162
 
163
+ logger.info("Carregando modelos na GPU...")
164
+ model_loaders = [CLIP_MODEL, VAE_MODEL, CLIP_VISION, UNET_MODEL]
165
+ model_management.load_models_gpu([
166
+ loader[0].patcher if hasattr(loader[0], 'patcher') else loader[0]
167
+ for loader in model_loaders
168
+ ])
169
+ logger.info("Modelos carregados com sucesso")
170
  except Exception as e:
171
+ logger.error(f"Erro ao inicializar modelos: {str(e)}")
172
+ raise
173
 
174
  # 9. Função de Geração
175
  @spaces.GPU
176
+ def generate_image(
177
+ prompt, input_image, lora_weight, guidance, downsampling_factor,
178
+ weight, seed, width, height, batch_size, steps,
179
+ progress=gr.Progress(track_tqdm=True)
180
+ ):
181
+ try:
182
+ # Aqui também: no_grad() para evitar cálculo de gradientes
183
+ with torch.no_grad():
184
+ logger.info(f"Iniciando geração com prompt: {prompt}")
185
 
186
+ # Codificar texto
187
+ cliptextencode = NODE_CLASS_MAPPINGS["CLIPTextEncode"]()
188
+ encoded_text = cliptextencode.encode(
189
+ text=prompt,
190
+ clip=CLIP_MODEL[0]
191
+ )
192
 
193
+ # Carregar e processar imagem
194
+ loadimage = NODE_CLASS_MAPPINGS["LoadImage"]()
195
+ loaded_image = loadimage.load_image(image=input_image)
196
+ if loaded_image is None:
197
+ raise ValueError("Erro ao carregar a imagem de entrada")
198
+ logger.info("Imagem carregada com sucesso")
199
 
200
+ # Flux Guidance
201
+ fluxguidance = NODE_CLASS_MAPPINGS["FluxGuidance"]()
202
+ flux_guidance = fluxguidance.append(
203
+ guidance=guidance,
204
+ conditioning=encoded_text[0]
205
+ )
206
 
207
+ # Redux Advanced
208
+ reduxadvanced = NODE_CLASS_MAPPINGS["ReduxAdvanced"]()
209
+ redux_result = reduxadvanced.apply_stylemodel(
210
+ downsampling_factor=downsampling_factor,
211
+ downsampling_function="area",
212
+ mode="keep aspect ratio",
213
+ weight=weight,
214
+ conditioning=flux_guidance[0],
215
+ style_model=STYLE_MODEL[0],
216
+ clip_vision=CLIP_VISION[0],
217
+ image=loaded_image[0]
218
+ )
219
 
220
+ # Criar latente vazio
221
+ emptylatentimage = NODE_CLASS_MAPPINGS["EmptyLatentImage"]()
222
+ empty_latent = emptylatentimage.generate(
223
+ width=width,
224
+ height=height,
225
+ batch_size=batch_size
226
+ )
227
 
228
+ # KSampler
229
+ logger.info("Iniciando sampling...")
230
+ ksampler = NODE_CLASS_MAPPINGS["KSampler"]()
231
+ sampled = ksampler.sample(
232
+ seed=seed,
233
+ steps=steps,
234
+ cfg=1,
235
+ sampler_name="euler",
236
+ scheduler="simple",
237
+ denoise=1,
238
+ model=UNET_MODEL[0],
239
+ positive=redux_result[0],
240
+ negative=flux_guidance[0],
241
+ latent_image=empty_latent[0]
242
+ )
243
 
244
+ # VAE Decode
245
+ logger.info("Decodificando imagem...")
246
+ vaedecode = NODE_CLASS_MAPPINGS["VAEDecode"]()
247
+ decoded = vaedecode.decode(
248
+ samples=sampled[0],
249
+ vae=VAE_MODEL[0]
250
+ )
251
 
252
+ # Salvar imagem
253
+ temp_filename = f"Flux_{random.randint(0, 99999)}.png"
254
+ temp_path = os.path.join(output_dir, temp_filename)
255
+ try:
256
+ Image.fromarray((decoded[0] * 255).astype("uint8")).save(temp_path)
257
+ logger.info(f"Imagem salva em: {temp_path}")
258
+ return temp_path
259
+ except Exception as e:
260
+ logger.error(f"Erro ao salvar imagem: {str(e)}")
261
+ return None
262
 
263
+ except Exception as e:
264
+ logger.error(f"Erro ao gerar imagem: {str(e)}")
265
+ return None
266
 
267
  # 10. Interface Gradio
268
  with gr.Blocks() as app:
269
+ gr.Markdown("# FLUX Redux Image Generator")
270
 
271
+ with gr.Row():
272
+ with gr.Column():
273
+ prompt_input = gr.Textbox(
274
+ label="Prompt",
275
+ placeholder="Enter your prompt here...",
276
+ lines=5
277
+ )
278
+ input_image = gr.Image(
279
+ label="Input Image",
280
+ type="filepath"
281
+ )
282
 
283
+ with gr.Row():
284
+ with gr.Column():
285
+ lora_weight = gr.Slider(
286
+ minimum=0,
287
+ maximum=2,
288
+ step=0.1,
289
+ value=0.6,
290
+ label="LoRA Weight"
291
+ )
292
+ guidance = gr.Slider(
293
+ minimum=0,
294
+ maximum=20,
295
+ step=0.1,
296
+ value=3.5,
297
+ label="Guidance"
298
+ )
299
+ downsampling_factor = gr.Slider(
300
+ minimum=1,
301
+ maximum=8,
302
+ step=1,
303
+ value=3,
304
+ label="Downsampling Factor"
305
+ )
306
+ weight = gr.Slider(
307
+ minimum=0,
308
+ maximum=2,
309
+ step=0.1,
310
+ value=1.0,
311
+ label="Model Weight"
312
+ )
313
+ with gr.Column():
314
+ seed = gr.Number(
315
+ value=random.randint(1, 2**64),
316
+ label="Seed",
317
+ precision=0
318
+ )
319
+ width = gr.Number(
320
+ value=1024,
321
+ label="Width",
322
+ precision=0
323
+ )
324
+ height = gr.Number(
325
+ value=1024,
326
+ label="Height",
327
+ precision=0
328
+ )
329
+ batch_size = gr.Number(
330
+ value=1,
331
+ label="Batch Size",
332
+ precision=0
333
+ )
334
+ steps = gr.Number(
335
+ value=20,
336
+ label="Steps",
337
+ precision=0
338
+ )
339
 
340
+ generate_btn = gr.Button("Generate Image")
341
 
342
+ with gr.Column():
343
+ output_image = gr.Image(label="Generated Image", type="filepath")
344
 
345
+ generate_btn.click(
346
+ fn=generate_image,
347
+ inputs=[
348
+ prompt_input,
349
+ input_image,
350
+ lora_weight,
351
+ guidance,
352
+ downsampling_factor,
353
+ weight,
354
+ seed,
355
+ width,
356
+ height,
357
+ batch_size,
358
+ steps
359
+ ],
360
+ outputs=[output_image]
361
+ )
362
 
363
  if __name__ == "__main__":
364
+ # Ajuste caso queira compartilhar publicamente, exemplo: app.launch(server_name="0.0.0.0", share=True)
365
+ app.launch()