--- title: PDF β†’ Manim β†’ LLM App emoji: "🎬" colorFrom: "red" colorTo: "blue" sdk: gradio sdk_version: "6.8.0" python_version: "3.11" app_file: app.py pinned: false --- # 🎬 PDF β†’ Manim Animation Pipeline A Hugging Face Spaces Gradio app that converts any PDF into an animated Manim video and delivers it to your inbox. --- ## πŸš€ Quick Start ### 1. Upload to Hugging Face Spaces Create a new Space on [huggingface.co/spaces](https://huggingface.co/spaces) with: - **SDK:** Gradio - **Hardware:** CPU Basic (or better β€” more RAM = faster renders) Upload all files in this folder. --- ### 2. Set Environment Secrets In your Space settings β†’ **Secrets**, add: | Secret Name | Value | |-----------------|--------------------------------------------| | `SMTP_EMAIL` | Your Gmail address (e.g. `you@gmail.com`) | | `SMTP_PASSWORD` | Gmail App Password (16-char, not login pw) | **How to get a Gmail App Password:** 1. Enable 2-Step Verification on your Google account. 2. Go to [myaccount.google.com/apppasswords](https://myaccount.google.com/apppasswords). 3. Create a new app password for "Mail". > ⚠️ **Never commit secrets to your repo.** Only use the Spaces secret store. --- ### 3. Usage 1. Open your Space URL. 2. Upload a PDF file. 3. Enter your email address *(saved in browser β€” no need to re-enter)*. 4. Enter your **Gemini API key** *(saved in browser)* β€” get one free at [aistudio.google.com](https://aistudio.google.com). 5. Click **Generate Video**. 6. Watch live status updates β€” the generated Manim code appears in-app, and the video arrives in your inbox! --- ## πŸ—οΈ Architecture ``` PDF Upload β”‚ β–Ό Extract Text (pypdf) β”‚ β–Ό Gemini 2.5 Flash (google-genai) β”‚ β†’ generated code shown live in UI β–Ό Manim Render (-qm, 1280Γ—720, 30fps) β”‚ β–Ό Video < 24MB? ──YES──▢ Email Attachment β”‚ β”‚ NO β”‚ β–Ό β”‚ Catbox.moe Upload β”‚ β”‚ β”‚ β–Ό β”‚ Email Link β—€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β–Ό Cleanup temp files ``` --- ## βš™οΈ Configuration | Setting | Default | Location | |--------------------|--------------|---------------------------------| | Max concurrent jobs| 100 | `app.py` β†’ `JobQueue(max_jobs=)`| | Thread workers | 8 | `app.py` β†’ `JobQueue(max_workers=)`| | Manim quality | `-qm` 720p30 | `pipeline.py` β†’ `_render_manim` | | Render timeout | 600s | `pipeline.py` β†’ `_render_manim` | | Catbox retries | 5 | `utils.py` | --- ## πŸ“ File Structure ``` . β”œβ”€β”€ app.py # Gradio UI + streaming status + BrowserState persistence β”œβ”€β”€ pipeline.py # Job pipeline orchestrator β”œβ”€β”€ queue_manager.py # Thread-pool queue with state tracking β”œβ”€β”€ utils.py # PDF, Gemini, email, Catbox helpers β”œβ”€β”€ requirements.txt # Python dependencies β”œβ”€β”€ packages.txt # System packages (LaTeX, ffmpeg, cairo…) └── README.md # This file ``` --- ## πŸ”’ Security Notes - Gemini API keys are passed per-request and **never stored server-side**. - Email/API key persisted in **browser localStorage** (client only). - SMTP credentials live only in HF Secrets (env vars). - All temporary files deleted after pipeline completion. - Each job uses a UUID to prevent path collisions. --- ## πŸ› Troubleshooting | Issue | Fix | |-------|-----| | `SMTP_EMAIL not set` | Add the secret in HF Space settings | | `latex not found` | Ensure `packages.txt` is in your Space root | | Render timeout | Use a higher-tier Space hardware | | Gemini API error | Check your API key and quota | | Empty PDF | PDF must have selectable text (not scanned image) | | Large video | Catbox fallback used automatically |