Skip to content

feat: synced lyrics via lrclib.net in a dedicated TUI panel #42

@gitcoder89431

Description

@gitcoder89431

Feature

Fetch and display time-synced lyrics (LRC format) in a dedicated panel in the TUI, scrolling automatically with playback position. Uses the free, open lrclib.net API — no auth required.

Why

Synced lyrics are a beloved feature in music players (Spotify, Apple Music, many terminal players). lrclib.net is a community-maintained, free API that returns LRC-format lyrics by artist + title — a perfect fit for tuitube since db.Track already has both fields. Zero cost, no API key, no rate limits for reasonable usage.

API

GET https://lrclib.net/api/get?artist_name={artist}&track_name={title}

Returns syncedLyrics (LRC format) and plainLyrics (fallback). LRC format:

[00:12.34] First line of lyrics
[00:15.00] Second line...

Implementation sketch

  1. On track start, fire a background goroutine: fetchLyrics(artist, title) []LrcLine
  2. Parse LRC timestamps into []struct{ TimeSec float64; Text string }
  3. Add a lyrics panel toggled by a keybind (e.g. l)
  4. In nowPlayingTick, find the current LRC line by binary-searching timePos against the timestamp slice
  5. Render in a scrollable lipgloss viewport — highlight current line, dim past/future lines
  6. Cache lyrics to ~/.cache/tuitube/lyrics/{youtube_id}.lrc to avoid re-fetching

Fallback chain

  1. Cached .lrc file
  2. lrclib.net synced lyrics
  3. lrclib.net plain lyrics (no scrolling, just display)
  4. "No lyrics found" empty state

Files likely affected

  • New internal/lyrics/lyrics.go package
  • internal/screens/ — new lyrics panel or overlay
  • internal/app/app.go — keybind + model field for lyrics visibility

Notes

  • Japanese/CJK track titles work well with lrclib since it matches by romanized title too
  • CleanTitle output from internal/sync/titles.go should be used for the API query, not the raw title

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions