Android app for 24/7 internet radio streaming with minimum latency, aggressive reconnection, and full Icecast/Shoutcast metadata support.
> [!IMPORTANT]
> This project was built with the assistance of [Cursor](https://cursor.com) (Claude Opus/Sonnet 4.6).
---
## Screenshots
| Station List | Now Playing | Mini-Player | Station Art Fallback |
|:---:|:---:|:---:|:---:|
|  |  |  |  |
- **Custom raw audio pipeline** — OkHttp → IcyParser → Mp3FrameSync → MediaCodec → AudioTrack for minimum latency (~26ms per MP3 frame)
- **Stay Connected mode** — aggressive reconnection with exponential backoff; never gives up until you say stop
- **Configurable buffer** — 0–500ms slider; 0ms keeps you as live as possible, higher values smooth out spotty connections
- **Icecast/Shoutcast metadata** — ICY protocol track title and artist extraction
- **Album art** — MusicBrainz/Cover Art Archive lookup with a fallback chain (ICY stream URL → station default art → station logo → placeholder)
### Station Management
- **SomaFM built-in** — full SomaFM catalog pre-loaded, sorted by listener count
- **Per-station stream quality** — choose 128/256 kbps and SSL/non-SSL per station, or set a global preference order
- **PLS/M3U import/export** — with `#EXTIMG` support for station artwork URLs
- **Tabs (playlists)** — pin/unpin, rename, and drag-to-reorder tabs and stations within them
- **Starring/favoriting** — starred stations sort to the top of their tab
### Now Playing Screen
- **Blurred album art background** — art fills the screen behind the player controls
- **Session timer** — total elapsed time since you hit play, not reset on reconnect
- **Connection timer** — elapsed time for the current TCP connection, resets on each reconnect
- **Latency indicator** — estimated stream-to-speaker latency in ms
- **Track history** — every track change is logged to the database with station and timestamp
- **Now Playing file logging** — optionally write track history to CSV, JSON Lines, or plain text
### System Integration
- **Media3 notification** — system media notification with album art, transport controls (play/stop + seek-to-live), lockscreen and Bluetooth headset support
- **Android Auto** — app registers as a media source; browse your playlists and stations from the car display
Exported files include `#EXTIMG` tags for stations that have a default artwork URL set.
---
## SomaFM
The SomaFM catalog is pre-loaded on first launch — no import needed. Stations are sorted by current listener count (refreshable with the sync button). You can set a global stream quality preference (256 kbps SSL recommended) or override it per station via long-press → Quality.
The audio engine is a standalone component with no Android framework dependencies. The service owns reconnection policy, Android Auto browse tree, and the Media3 session. The UI observes state via `StateFlow` and never touches the engine directly.
For full detail see the [design document](docs/plans/2026-03-09-android-247-radio-design.md) and [Media3/Android Auto design](docs/plans/2026-03-18-media3-android-auto-design.md).
---
## Tech Stack
| Layer | Library |
|---|---|
| Language | Kotlin |
| UI | Jetpack Compose, Material Design 3 |
| Media session / Auto | AndroidX Media3 (media3-session, media3-common) |