Spaces:
Paused
Paused
| import gradio as gr | |
| import torch | |
| import random | |
| import time | |
| from transformers import AutoTokenizer, AutoModelForCausalLM | |
| from diffusers import DiffusionPipeline, LCMScheduler | |
| from PIL import Image, ImageFilter | |
| # ------------------------------- | |
| # SMALL PROMPT ENHANCER (CPU) | |
| # ------------------------------- | |
| ENHANCER_MODEL = "HuggingFaceTB/SmolLM-135M-Instruct" | |
| tokenizer_enhancer = AutoTokenizer.from_pretrained(ENHANCER_MODEL) | |
| model_enhancer = AutoModelForCausalLM.from_pretrained(ENHANCER_MODEL) | |
| def enhance_text(user_prompt, prefix): | |
| """ | |
| Uses a tiny LLM to rewrite user input into a more detailed instruction. | |
| """ | |
| instruction = f"Rewrite this for an image generator with detail: {user_prompt}" | |
| if prefix: | |
| instruction = f"{prefix} {user_prompt}" | |
| inputs = tokenizer_enhancer(instruction, return_tensors="pt") | |
| outputs = model_enhancer.generate( | |
| **inputs, | |
| max_new_tokens=50, | |
| temperature=0.7, | |
| do_sample=True | |
| ) | |
| text = tokenizer_enhancer.decode(outputs[0], skip_special_tokens=True) | |
| return text.strip() | |
| # ------------------------------- | |
| # IMAGE MODEL SETUP (CPU SAFE) | |
| # ------------------------------- | |
| IMG_MODEL_ID = "runwayml/stable-diffusion-v1-5" | |
| IMG_ADAPTER_ID = "latent-consistency/lcm-lora-sdv1-5" | |
| pipe = DiffusionPipeline.from_pretrained( | |
| IMG_MODEL_ID, | |
| torch_dtype=torch.float32, | |
| safety_checker=None | |
| ) | |
| pipe.scheduler = LCMScheduler.from_config(pipe.scheduler.config) | |
| pipe.load_lora_weights(IMG_ADAPTER_ID) | |
| pipe.to("cpu") | |
| pipe.enable_attention_slicing() | |
| pipe.enable_vae_slicing() | |
| pipe.set_progress_bar_config(disable=True) | |
| # ------------------------------- | |
| # ETA | |
| # ------------------------------- | |
| def estimate_time(steps, resolution): | |
| steps = int(steps) | |
| resolution = int(resolution) | |
| per_step = {512:12, 768:25, 1024:45}[resolution] | |
| overhead = 2 | |
| est = overhead + steps * per_step | |
| mins = est // 60 | |
| secs = est % 60 | |
| return f"⏱️ Estimated: ~{mins}m {secs}s" | |
| # ------------------------------- | |
| # GENERATE WITH PROGRESSIVE BLUR | |
| # ------------------------------- | |
| def generate(prompt, neg_prompt, resolution, steps): | |
| # 1️⃣ AI PROMPT ENHANCEMENT | |
| enhanced_prompt = enhance_text(prompt, "") | |
| enhanced_negative = enhance_text(neg_prompt, "Rewrite negative prompt:") | |
| # 2️⃣ White placeholder | |
| placeholder = Image.new("RGB", (int(resolution), int(resolution)), (255,255,255)) | |
| yield [placeholder], "🟡 Generating..." | |
| # 3️⃣ CPU IMAGE GENERATION | |
| seed = random.randint(0, 10**9) | |
| gen = torch.Generator("cpu").manual_seed(seed) | |
| pipe.scheduler.set_timesteps(int(steps)) | |
| img = pipe( | |
| prompt=enhanced_prompt, | |
| negative_prompt=enhanced_negative, | |
| num_inference_steps=int(steps), | |
| guidance_scale=1.2, | |
| width=int(resolution), | |
| height=int(resolution), | |
| generator=gen | |
| ).images[0] | |
| # 4️⃣ BLUR REVEAL | |
| max_blur = 20 | |
| for i in range(10): | |
| blur_pct = 100 - i*10 | |
| blurred = img.filter(ImageFilter.GaussianBlur(radius=max_blur * blur_pct/100)) | |
| yield [blurred], "🟢 Revealing..." | |
| time.sleep(1) | |
| # 5️⃣ FINAL | |
| yield [img], f"✅ Done | Seed: {seed}" | |
| # ------------------------------- | |
| # GRADIO UI | |
| # ------------------------------- | |
| with gr.Blocks(theme=gr.themes.Soft()) as demo: | |
| gr.Markdown("# 👾 CREEPER AI — SMART IMAGE GENERATOR") | |
| gr.Markdown("1: The higher the resolution & steps, the longer the image takes to make.\n2: The more detailed the prompt and negative prompt, the better the result.") | |
| with gr.Row(): | |
| with gr.Column(): | |
| prompt_in = gr.Textbox(label="Prompt") | |
| neg_in = gr.Textbox(label="Negative Prompt") | |
| resolution = gr.Radio([512, 768, 1024], value=512, label="Resolution") | |
| steps = gr.Slider(6,8,value=6,step=1,label="Steps") | |
| eta = gr.Markdown("⏱️ Estimated: ~1m 0s") | |
| gen_btn = gr.Button("Generate") | |
| status = gr.Markdown("🟢 Ready") | |
| with gr.Column(): | |
| gallery = gr.Gallery(columns=1) | |
| for ctrl in [steps, resolution]: | |
| ctrl.change(estimate_time, [steps, resolution], eta) | |
| gen_btn.click( | |
| generate, | |
| inputs=[prompt_in, neg_in, resolution, steps], | |
| outputs=[gallery, status] | |
| ) | |
| demo.launch() | |