imagecaptioningai / README.md
LovnishVerma's picture
Update README.md
c79b5ad verified
|
Raw
History Blame Contribute Delete
10.9 kB
---
title: EchoLens 2.0
emoji: 🌍
colorFrom: purple
colorTo: blue
sdk: gradio
sdk_version: 5.34.2
app_file: app.py
pinned: true
license: apache-2.0
short_description: Image to Caption
---
# πŸ‘οΈ EchoLens 2.0 β€” Realtime Vision Assistant for Blind & Low-Vision Users
[![Hugging Face Spaces](https://img.shields.io/badge/%F0%9F%A4%97%20Hugging%20Face-Spaces-blue)](https://lovnishverma-imagecaptioningai.hf.space/)
[![License: Apache 2.0](https://img.shields.io/badge/License-Apache%202.0-green.svg)](https://opensource.org/licenses/Apache-2.0)
[![Gradio](https://img.shields.io/badge/Gradio-5.34.2-orange)](https://gradio.app)
[![Model: Florence-2](https://img.shields.io/badge/Model-Florence--2--base-purple)](https://huggingface.co/microsoft/Florence-2-base)
**EchoLens** is an accessible, real-time vision assistant that helps blind and low-vision users understand their surroundings through AI-powered image captioning and text-to-speech. Point a webcam at the world, and EchoLens describes what it sees β€” out loud.
---
## ✨ Features
- **🎯 Instant scene description** β€” Press `D` or click *Describe Now* to hear what the camera sees
- **πŸ”„ Realtime mode** β€” Auto-describes the scene every 3.5 seconds; skips unchanged frames using perceptual hashing (dHash)
- **🧠 5 vision tasks** β€” Quick Caption, Describe Scene, Detailed Description, OCR (text reading), and Object Detection with spatial positions (left / center / right)
- **πŸ—£οΈ Natural-sounding TTS** β€” Powered by Microsoft Edge TTS with 5 voice options across US and UK accents
- **πŸ“ Image upload support** β€” Upload a photo from disk for immediate description
- **πŸ” Repeat last description** β€” Press `P` to replay the last audio at any time
- **β™Ώ Accessible UI** β€” Font size controls (A / A+ / A++), high-contrast toggle, full keyboard shortcuts, and ARIA live regions for screen-reader compatibility
- **πŸ“Š Session statistics** β€” Track manual describes, realtime captures, and history
- **⚑ Smart scene-change detection** β€” Only re-describes when the scene actually changes, saving compute and reducing audio fatigue
- **πŸ–₯️ GPU & CPU support** β€” Auto-detects CUDA, MPS (Apple Silicon), or CPU; optimized dtype per device
---
## 🎹 Keyboard Shortcuts
| Key | Action |
|-----|--------|
| `D` | Describe what the camera sees right now |
| `R` | Toggle realtime auto-description on/off |
| `P` | Repeat the last description |
| `Esc` | Stop all audio and exit realtime mode |
> Shortcuts work globally β€” no need to focus any UI element first. They are disabled while typing in text fields.
---
## 🧠 Vision Tasks
| Task | Token | Description |
|------|-------|-------------|
| **Quick Caption** | `<CAPTION>` | Short one-line summary of the scene |
| **Describe Scene** | `<DETAILED_CAPTION>` | Detailed multi-sentence description |
| **Detailed Description** | `<MORE_DETAILED_CAPTION>` | Thorough paragraph-length description |
| **Read Text (OCR)** | `<OCR>` | Reads any text visible in the image (signs, labels, screens) |
| **Detect Objects** | `<OD>` | Lists detected objects and their spatial positions |
### Object Detection Output Example
> *"I see person in the center, cup on the right, laptop on the left, and book on the left."*
The spatial positions (left / center / right) are computed from Florence-2's bounding-box coordinates, giving users a sense of *where* things are, not just *what* things are.
---
## πŸ—£οΈ Available Voices
| Voice | Locale | Gender |
|-------|--------|--------|
| Aria β€” Female, US | `en-US` | Female |
| Guy β€” Male, US | `en-US` | Male |
| Jenny β€” Female, US | `en-US` | Female |
| Sonia β€” Female, UK | `en-GB` | Female |
| Ryan β€” Male, UK | `en-GB` | Male |
---
## πŸ—οΈ Architecture
```
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚ Webcam Feed ─────┐ β”‚
β”‚ Image Upload ────┼──► Preprocess (resize, enhance) β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚ β”‚
β–Ό β”‚
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚
β”‚ dHash Check │◄──────────────
β”‚ (scene change?) β”‚ β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚
β”‚ β”‚
unchanged β”€β”€β”€β”€β”€β”˜ β”‚
changed ───────► Florence-2-base β”‚
(Microsoft) β”‚
β”œβ”€ <CAPTION> β”‚
β”œβ”€ <DETAILED_CAPTION> β”‚
β”œβ”€ <MORE_DETAILED_CAPTION>
β”œβ”€ <OCR> β”‚
└─ <OD> ──► spatial β”‚
formatter β”‚
β”‚
β”‚ β”‚
β–Ό β”‚
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚
β”‚ Edge TTS (async) β”‚ β”‚
β”‚ dedicated thread β”‚ β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”¬β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚
β”‚ β”‚
β–Ό β”‚
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β” β”‚
β”‚ Gradio Audio β”‚ β”‚
β”‚ (autoplay) β”‚ β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜ β”‚
```
**Scene-change detection** uses dHash (difference hash) with a configurable Hamming-distance threshold (`SCENE_THRESHOLD = 0.12`). If the new frame is β‰₯88% similar to the previous one, the inference is skipped β€” reducing unnecessary compute and audio fatigue.
**Dedicated TTS event loop** β€” Edge-TTS runs on its own asyncio event loop in a background thread, so speech generation never blocks the vision model or the UI.
---
## πŸš€ Getting Started
### Run on Hugging Face Spaces
1. Click **"Duplicate this Space"** (top-right on the Hugging Face page)
2. Set visibility to **Public** or **Private**
3. Wait for the build (~2–3 minutes on first launch)
4. Open the app β€” no installation needed!
### Run locally
```bash
# 1. Clone
# git clone <your-repo-url>
cd echolens
# 2. Install dependencies
pip install -r requirements.txt
# 3. Launch
python app.py
```
The app will be available at `http://localhost:7860`.
> **Note:** The first launch downloads the Florence-2-base model (~460 MB) and performs a background warmup inference. Expect a short delay before the first description.
---
## πŸ“¦ Requirements
```
transformers==4.48.0
timm
torch>=2.1.0
torchvision
Pillow>=10.0.0
einops
edge-tts
gradio==5.34.2
numpy
accelerate
```
GPU (CUDA) is used automatically if available; the app falls back to CPU otherwise. On Apple Silicon, MPS is used.
---
## βš™οΈ Configuration
All tunable constants live in the `Config` class at the top of `app.py`:
| Constant | Default | Description |
|----------|---------|-------------|
| `CAPTURE_INTERVAL` | `3.5` | Seconds between realtime captures |
| `SCENE_THRESHOLD` | `0.12` | dHash distance below which a scene is treated as unchanged |
| `MAX_DIM` | `768` | Max image dimension before inference (larger images are downscaled) |
| `TTS_RATE` | `+8%` | Speech speed adjustment for Edge TTS |
| `DEBOUNCE_S` | `0.8` | Minimum seconds between processing frames (prevents rapid-fire) |
---
## β™Ώ Accessibility Design
EchoLens is built with accessibility as a first-class concern:
| Feature | Implementation |
|---------|---------------|
| **ARIA live regions** | Screen readers auto-announce new descriptions via `aria-live="assertive"` |
| **Keyboard-first** | All core actions reachable without a mouse (D/R/P/Esc) |
| **Font scaling** | Three size levels (A / A+ / A++) via CSS class toggles on `<body>` |
| **High contrast mode** | One-click toggle; increases contrast 1.7Γ— and adds dark borders |
| **Autoplay audio** | Descriptions play immediately; no extra click needed |
| **Large touch targets** | Buttons β‰₯52 px height; full-width on mobile |
| **Focus indicators** | Visible 3 px focus rings on all interactive elements |
| **Status feedback** | Real-time status bar shows processing state, cache hits, word counts |
| **Screen-reader announcements** | JavaScript pushes button-action feedback to the ARIA live region |
---
## πŸ§ͺ Development
### Project structure
```
.
β”œβ”€β”€ app.py # Main Gradio application
β”œβ”€β”€ requirements.txt # Python dependencies
β”œβ”€β”€ README.md # This file
└── LICENSE # Apache 2.0
```
### Adding a new voice
Add an entry to `VOICE_MAP` in `app.py`:
```python
VOICE_MAP = {
# ... existing voices ...
"New Voice β€” Female, CA": "en-CA-ClaraNeural",
}
```
Find available voices with `edge-tts --list-voices`.
### Adding a new task
1. Add to `TASKS` (human label β†’ Florence-2 token)
2. Add to `TASK_INFO` (tooltip description)
3. Set `MAX_TOKENS` for the token if needed
4. Add formatting logic in `_infer()` if the task needs custom output parsing
---
## πŸ€– Model
[Microsoft Florence-2-base](https://huggingface.co/microsoft/Florence-2-base) β€” a unified vision-language model that handles captioning, OCR, and object detection through task-specific prompt tokens. Runs in `float16` on CUDA and `float32` on CPU/MPS.
---
## πŸ“„ License
Apache 2.0 β€” see [LICENSE](LICENSE) for details.
---
## πŸ™ Acknowledgements
- [Microsoft Florence-2](https://huggingface.co/microsoft/Florence-2-base) for the vision-language model
- [Edge TTS](https://github.com/rany2/edge-tts) for free, high-quality neural text-to-speech
- [Gradio](https://gradio.app) for the accessible web UI framework
- [Hugging Face](https://huggingface.co) for model hosting and Spaces infrastructure
- [Transformers](https://github.com/huggingface/transformers) for the model inference pipeline