fix(android): notification art uses album cover, not embedded stream tags #84

Merged
bvandeusen merged 1 commits from dev into main 2026-06-04 22:35:21 -04:00
Owner

Same-day re-cut on the per-day mutable CalVer scheme (post-v2026.06.04 papercut).

Notification / lock-screen art now matches the in-app album cover

On-device observation: the MediaController notification and lock-screen background showed a different album cover than the in-app surfaces for some tracks.

Root cause — two different art sources:

  • In-app covers come from TrackRef.coverUrl/api/albums/{id}/cover (server album-level art).
  • The notification art came from the stream's embedded ID3/FLAC tags (MediaMetadata.artworkData), because PlayerController.toMediaItem never set artworkUri. Media3's BitmapLoader.loadBitmapFromMetadata prefers artworkData over artworkUri, and ExoPlayer extracts embedded picture frames into the live metadata. For tracks whose embedded tag art differs from the server album cover (compilations, re-grouped singles), the two surfaces disagreed.

Fix (3 files):

  • PlayerController.toMediaItem — set artworkUri to coverUrl. Verified against Media3 1.10.1 source: MediaMetadata.Builder.populate() overwrites artworkUri + artworkData as an atomic pair, and ExoPlayerImpl.buildUpdatedMediaMetadata layers MediaItem metadata over stream metadata — so the MediaItem URI clears the embedded artworkData. Album cover wins on both surfaces.
  • PlayerFactory.buildBitmapLoader — OkHttp-backed CacheBitmapLoader(DataSourceBitmapLoader(...)) so the authed placeholder.invalid cover URL resolves (Media3's default DefaultHttpDataSource loader can't rewrite the host or attach the auth cookie). CacheBitmapLoader dedupes refetches across metadata refreshes.
  • MinstrelPlayerService — attach via MediaSession.Builder.setBitmapLoader.

Net: notification, lock screen, BT/AVRCP, Auto, Pixel Watch all show the same album cover as the app regardless of file tags.

Verify on device

  • Play a track whose embedded tag art differs from its server album cover (a compilation or re-grouped single) → notification / lock-screen background now matches the in-app cover.

🤖 Generated with Claude Code

Same-day re-cut on the per-day mutable CalVer scheme (post-v2026.06.04 papercut). ## Notification / lock-screen art now matches the in-app album cover On-device observation: the MediaController notification and lock-screen background showed a *different* album cover than the in-app surfaces for some tracks. **Root cause — two different art sources:** - In-app covers come from `TrackRef.coverUrl` → `/api/albums/{id}/cover` (server album-level art). - The notification art came from the **stream's embedded ID3/FLAC tags** (`MediaMetadata.artworkData`), because `PlayerController.toMediaItem` never set `artworkUri`. Media3's `BitmapLoader.loadBitmapFromMetadata` prefers `artworkData` over `artworkUri`, and ExoPlayer extracts embedded picture frames into the live metadata. For tracks whose embedded tag art differs from the server album cover (compilations, re-grouped singles), the two surfaces disagreed. **Fix (3 files):** - `PlayerController.toMediaItem` — set `artworkUri` to `coverUrl`. Verified against Media3 1.10.1 source: `MediaMetadata.Builder.populate()` overwrites `artworkUri` + `artworkData` as an atomic pair, and `ExoPlayerImpl.buildUpdatedMediaMetadata` layers MediaItem metadata over stream metadata — so the MediaItem URI **clears** the embedded `artworkData`. Album cover wins on both surfaces. - `PlayerFactory.buildBitmapLoader` — OkHttp-backed `CacheBitmapLoader(DataSourceBitmapLoader(...))` so the authed `placeholder.invalid` cover URL resolves (Media3's default `DefaultHttpDataSource` loader can't rewrite the host or attach the auth cookie). `CacheBitmapLoader` dedupes refetches across metadata refreshes. - `MinstrelPlayerService` — attach via `MediaSession.Builder.setBitmapLoader`. Net: notification, lock screen, BT/AVRCP, Auto, Pixel Watch all show the same album cover as the app regardless of file tags. ## Verify on device - Play a track whose embedded tag art differs from its server album cover (a compilation or re-grouped single) → notification / lock-screen background now matches the in-app cover. 🤖 Generated with [Claude Code](https://claude.com/claude-code)
bvandeusen added 1 commit 2026-06-04 22:35:16 -04:00
fix(android): notification art uses album cover, not embedded stream tags
android / Build + lint + test (push) Successful in 3m38s
58810a860b
The MediaController notification / lock-screen background pulled artwork
from the stream's embedded ID3/FLAC tags (artworkData) because the
MediaItem never set artworkUri — a different source than the in-app
album cover (/api/albums/{id}/cover). For tracks whose embedded tag art
differs from the server album cover, the two surfaces disagreed.

- PlayerController.toMediaItem: set artworkUri to TrackRef.coverUrl.
  MediaMetadata.populate() overwrites artworkUri+artworkData as a pair,
  so the MediaItem URI clears the embedded bytes ExoPlayer extracts from
  the stream — the album cover now wins on both surfaces.
- PlayerFactory.buildBitmapLoader: OkHttp-backed CacheBitmapLoader so the
  authed placeholder cover URL resolves (the default DefaultHttpDataSource
  loader can't rewrite placeholder.invalid or attach the auth cookie).
- MinstrelPlayerService: attach it via MediaSession.setBitmapLoader.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
bvandeusen merged commit 4d8c7d6566 into main 2026-06-04 22:35:21 -04:00
Sign in to join this conversation.
No Reviewers
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: bvandeusen/minstrel#84