diff --git a/backend/mpris.go b/backend/mpris.go index 39bd08c..e60809c 100644 --- a/backend/mpris.go +++ b/backend/mpris.go @@ -208,11 +208,11 @@ func (m *MPRISHandler) PlaybackStatus() (types.PlaybackStatus, error) { func (m *MPRISHandler) LoopStatus() (types.LoopStatus, error) { switch m.pm.GetLoopMode() { - case player.LoopAll: + case LoopAll: return types.LoopStatusPlaylist, nil - case player.LoopOne: + case LoopOne: return types.LoopStatusTrack, nil - case player.LoopNone: + case LoopNone: return types.LoopStatusNone, nil } return "", errors.New("unknown loop status") @@ -221,13 +221,15 @@ func (m *MPRISHandler) LoopStatus() (types.LoopStatus, error) { func (m *MPRISHandler) SetLoopStatus(status types.LoopStatus) error { switch status { case types.LoopStatusPlaylist: - return m.pm.SetLoopMode(player.LoopAll) + m.pm.SetLoopMode(LoopAll) case types.LoopStatusTrack: - return m.pm.SetLoopMode(player.LoopOne) + m.pm.SetLoopMode(LoopOne) case types.LoopStatusNone: - return m.pm.SetLoopMode(player.LoopNone) + m.pm.SetLoopMode(LoopNone) + default: + return errors.New("unknown loop status") } - return errors.New("unknown loop status") + return nil } func (m *MPRISHandler) Rate() (float64, error) { diff --git a/backend/playbackmanager.go b/backend/playbackmanager.go index e568544..597aeb9 100644 --- a/backend/playbackmanager.go +++ b/backend/playbackmanager.go @@ -19,9 +19,17 @@ var ( ReplayGainAuto = "Auto" ) -// A high-level Subsonic-aware playback backend. -// Manages loading tracks into the Player queue, -// sending callbacks on play time updates and track changes. +// The playback loop mode (LoopNone, LoopAll, LoopOne). +type LoopMode int + +const ( + LoopNone LoopMode = iota + LoopAll + LoopOne +) + +// A high-level MediaProvider-aware playback engine, serves as an +// intermediary between the frontend and various Player backends. type PlaybackManager struct { ctx context.Context cancelPollPos context.CancelFunc @@ -35,6 +43,7 @@ type PlaybackManager struct { playQueue []*mediaprovider.Track nowPlayingIdx int + loopMode LoopMode // to pass to onSongChange listeners; clear once listeners have been called lastScrobbled *mediaprovider.Track @@ -45,7 +54,7 @@ type PlaybackManager struct { // registered callbacks onSongChange []func(nowPlaying, justScrobbledIfAny *mediaprovider.Track) onPlayTimeUpdate []func(float64, float64) - onLoopModeChange []func(player.LoopMode) + onLoopModeChange []func(LoopMode) onVolumeChange []func(int) onSeek []func() onPaused []func() @@ -157,7 +166,7 @@ func (p *PlaybackManager) OnPlayTimeUpdate(cb func(float64, float64)) { } // Registers a callback that is notified whenever the loop mode changes. -func (p *PlaybackManager) OnLoopModeChange(cb func(player.LoopMode)) { +func (p *PlaybackManager) OnLoopModeChange(cb func(LoopMode)) { p.onLoopModeChange = append(p.onLoopModeChange, cb) } @@ -406,44 +415,29 @@ func (p *PlaybackManager) SetReplayGainMode(mode player.ReplayGainMode) { // Changes the loop mode of the player to the next one. // Useful for toggling UI elements, to change modes without knowing the current player mode. -func (p *PlaybackManager) SetNextLoopMode() error { - var err error - switch p.GetLoopMode() { - case player.LoopNone: - err = p.SetLoopMode(player.LoopAll) - case player.LoopAll: - err = p.SetLoopMode(player.LoopOne) - case player.LoopOne: - err = p.SetLoopMode(player.LoopNone) - default: - return nil - } +func (p *PlaybackManager) SetNextLoopMode() { + switch p.loopMode { + case LoopNone: + p.SetLoopMode(LoopAll) + case LoopAll: + p.SetLoopMode(LoopOne) + case LoopOne: + p.SetLoopMode(LoopNone) - if err != nil { - return err } - //for _, cb := range p.onLoopModeChange { - // cb(p.player.GetLoopMode()) - //} - - return nil } -func (p *PlaybackManager) SetLoopMode(loopMode player.LoopMode) error { - //if err := p.player.SetLoopMode(player.LoopMode(loopMode)); err != nil { - // return err - //} +func (p *PlaybackManager) SetLoopMode(loopMode LoopMode) { + p.loopMode = loopMode + // TODO: update next track if needed for _, cb := range p.onLoopModeChange { cb(loopMode) } - - return nil } -func (p *PlaybackManager) GetLoopMode() player.LoopMode { - return 0 - //return p.player.GetLoopMode() +func (p *PlaybackManager) GetLoopMode() LoopMode { + return p.loopMode } func (p *PlaybackManager) PlayerStatus() player.Status { diff --git a/player/player.go b/player/player.go index b944904..4e3683a 100644 --- a/player/player.go +++ b/player/player.go @@ -57,15 +57,6 @@ type Status struct { PlaylistPos int } -// The playback loop mode (LoopNone, LoopAll, LoopOne). -type LoopMode int - -const ( - LoopNone LoopMode = iota - LoopAll - LoopOne -) - type ReplayGainMode int const ( @@ -92,15 +83,3 @@ func (r ReplayGainMode) String() string { return "no" } } - -func (l LoopMode) String() string { - switch l { - case LoopNone: - return "no" - case LoopAll: - return "all" - case LoopOne: - return "one" - } - return "UNKNOWN_LOOP_MODE" -} diff --git a/ui/widgets/auxcontrols.go b/ui/widgets/auxcontrols.go index 88102da..1f5d63b 100644 --- a/ui/widgets/auxcontrols.go +++ b/ui/widgets/auxcontrols.go @@ -7,7 +7,7 @@ import ( "fyne.io/fyne/v2/theme" "fyne.io/fyne/v2/widget" - "github.com/dweymouth/supersonic/player" + "github.com/dweymouth/supersonic/backend" myTheme "github.com/dweymouth/supersonic/ui/theme" "github.com/dweymouth/supersonic/ui/util" ) @@ -67,15 +67,15 @@ func (a *AuxControls) OnChangeLoopMode(f func()) { a.loop.OnTapped = f } -func (a *AuxControls) SetLoopMode(mode player.LoopMode) { +func (a *AuxControls) SetLoopMode(mode backend.LoopMode) { switch mode { - case player.LoopAll: + case backend.LoopAll: a.loop.Importance = widget.HighImportance a.loop.Icon = myTheme.RepeatIcon - case player.LoopOne: + case backend.LoopOne: a.loop.Importance = widget.HighImportance a.loop.Icon = myTheme.RepeatOneIcon - case player.LoopNone: + case backend.LoopNone: a.loop.Importance = widget.MediumImportance a.loop.Icon = myTheme.RepeatIcon }