Commit Graph
28 Commits
Author SHA1 Message Date
zarzet 040c328479 feat(widgets): add native Android and iOS home screen players
Publish artwork, metadata, and transport state through a shared Dart bridge. Add configurable Android RemoteViews and iOS WidgetKit players with controls and links into the full player.

Serialize widget commands and session restoration, and share one headless-capable iOS Flutter engine with the foreground scene. Include native integration tests, Dart bridge tests, and widget setup documentation.
2026-09-25 01:22:58 +07:00
zarzet 5b519070a3 feat(player): add beat-matched AutoMix and refine Mornye navigation
Add default-off local beat analysis, pitch-preserving tempo matching, crossfade fallback, and cancellation-safe two-deck playback. Expose AutoMix in settings and the Mornye queue.

Separate Search from Home, remove the Mornye greeting, and keep Home/Search icons moving continuously between full and compact navigation. Restore expansion on upward Library scrolling.

Validate beat analysis, transport handoff and cancellation, settings persistence, and navigation behavior. Flutter analysis and the signed iOS simulator build pass.
2026-09-20 20:36:26 +07:00
zarzet 63e1a9b9c8 feat(ui): add Mornye glass theme and adaptive music player
Add a selectable Mornye theme with shared glass controls, dialogs, sheets, notifications, and collection headers while retaining Material components.

Update player artwork, lyrics transitions and highlighting, synchronized rolling time labels, volume controls, and compact navigation. Unify metadata, Library, search, and extension surfaces; preserve restored artwork and report extension load failures.

Validation: full Flutter analyzer clean; 713 tests passed and 4 skipped; pinned Dart formatting and diff checks passed; signed ARM64 and ARM32 release APKs built and verified.
2026-09-19 12:10:10 +07:00
zarzet f0ed293d48 feat: add opt-in Discord Rich Presence on Android
Use the official Discord Social SDK through JNI to share built-in player activity, clear presence when playback stops, and guard against late callbacks after disabling. Package the SDK optionally through SPOTIFLAC_DISCORD_SDK_DIR with license notices.

Credit: @itsmegaaa for the Rich Presence initiative and contribution in #575 and #576.

Validation: 15 Dart tests, scoped Flutter analysis, and one Android 16 ARM64 SDK/JNI instrumentation test passed. Visible presence on a signed-in Discord profile remains unverified.
2026-09-17 02:12:24 +07:00
zarzet bfffb8da11 fix(replaygain): write and verify native Opus gain tags
Preserve audio and artwork while replacing conflicting Opus gain tags with R128 comments. Verify manual, download, and album writes, handle SAF failures, and refresh playback normalization after saving.
2026-09-06 21:03:57 +07:00
zarzet 3d35058b02 fix(playback): retain ReplayGain for SAF descriptor leases
Carry the original display name through playback leases to format-aware metadata reads. Cache successful normalization results by source identity, bound the cache, and retry transient read failures.

Add regressions for descriptor hints, album gain fallback, and failed-read retries.
2026-09-06 14:04:04 +07:00
zarzet a1ee346f2f chore(logging): sanitize diagnostics and reduce noise 2026-08-31 01:49:49 +07:00
zarzet 91b2de8175 perf(playback): stream SAF tracks through descriptor leases 2026-08-30 23:18:03 +07:00
zarzet 29a86b0dc3 feat(player): add sleep timer 2026-08-30 17:23:16 +07:00
zarzet a926a2825b fix(player): handle headset media controls 2026-08-30 17:04:41 +07:00
zarzet 45d9bbd7b2 perf: harden download and persistence lifecycle 2026-08-28 12:51:03 +07:00
zarzet 433f8ed685 perf: reduce queue and extension runtime overhead 2026-08-28 01:47:51 +07:00
zarzet 19591bdf19 feat(metadata): show explicit badges in track titles 2026-08-22 23:08:40 +07:00
zarzet 5228b0030b fix(player): restore lyrics after cold start 2026-07-30 13:48:05 +07:00
zarzet 04a8700a65 fix(player): restore playback position reliably 2026-07-29 21:03:11 +07:00
zarzet 24b9d7ba80 fix(player): preserve audio quality across track changes 2026-07-29 19:29:19 +07:00
zarzet 1e973d5ecb style(dart): apply repository formatting 2026-07-29 14:14:42 +07:00
zarzet 8d077ae2da feat(player): add repeat off/all/one modes
The internal player handles setRepeatMode: repeat-one replays the
current track, repeat-all wraps the queue (and keeps a single-track
shuffle queue alive). The mode is broadcast in playback state,
persisted with the playback session, and toggleable from the Now
Playing transport row and the up-next sheet; a small shuffle toggle
joins the transport row for symmetry.
2026-07-26 19:00:50 +07:00
zarzet 54dcdb92dd feat(player): restore playback session after process death
Queue, current index, position, and shuffle flag are snapshotted to a
new app_state playback_session table on pause, track change, and queue
mutation (never on position ticks). On launch the session is restored
paused into the mini player; the first play seeks to the saved
position. Plain file paths that no longer exist are dropped, an
explicit stop or mini-player dismiss clears the snapshot, and the
installation-restore guard wipes it alongside the download queue.
2026-07-26 17:45:50 +07:00
zarzet 7f1c3e60db fix(player): prevent stale playback and clean SAF temps 2026-07-15 21:32:07 +07:00
zarzet 9ac10dd6bb feat(player): ReplayGain/R128 volume normalization for the built-in player
Reads REPLAYGAIN_TRACK_GAIN (album gain fallback) from FLAC/MP3/M4A tags
and converts Opus R128_TRACK_GAIN/R128_ALBUM_GAIN (Q7.8, -23 LUFS) to the
same ReplayGain dB representation on the Go side, then attenuates the
internal player's volume per track. Off by default; toggle lives under
Library > Playback. Opus header output gain is left to the decoder, which
already applies it.

Closes #465
2026-07-14 15:18:42 +07:00
zarzet 4caf875da4 Revert "fix(player): don't auto-resume after interruption while backgrounded"
This reverts commit 09714e3c64b22ccdc8a6555ffd6398b9cd205f23.
2026-07-14 09:10:18 +07:00
zarzet a7f9aae0a9 fix(player): don't auto-resume after interruption while backgrounded 2026-07-14 09:10:17 +07:00
zarzet 7573d360bf feat(player): swipe the mini player away to stop playback
Horizontal Dismissible on the bar; stop() now also clears the current
media item so the bar (and any listener of it) sees the session end.
2026-07-14 09:10:15 +07:00
zarzet ae8638a4b2 chore(player): log internal pause and audio interruption events
Add debug/info logging around audio focus interruptions, becoming-noisy
events, and user pause requests to make preview playback issues easier
to diagnose.
2026-06-30 06:20:51 +07:00
zarzet 1cd668c869 l10n: localize library settings and announcements
Move hardcoded strings in library settings, announcement link errors,
and unknown track title/artist fallbacks to AppLocalizations. Sync
locale-dependent fallback strings from MainShell.
2026-06-30 05:10:34 +07:00
zarzet 1550eedc12 feat: reorderable up-next queue + playback stability
- Up Next sheet supports drag-to-reorder via ReorderableListView with
  drag handles; MusicPlayerHandler.moveQueueItem keeps current track active
- Active lyric line centers higher in viewport (0.35) so it sits visually
  centered instead of leaning low
- Audio focus rework: explicit music AudioContext, ignore duck
  interruptions, drop the fragile ignore-complete timer, recover playback
  on transient stop/complete during track switches
2026-06-29 06:46:31 +07:00
zarzet 3a2481e8b2 feat: add new playback experience and media integration 2026-06-28 22:22:33 +07:00