From 196f7f2cff62f9da1ee038d0bc4347b3d36483ec Mon Sep 17 00:00:00 2001 From: Michael Manganiello Date: Tue, 20 Jun 2023 22:56:48 -0300 Subject: [PATCH 1/2] Add functionality to repeat current track This new Loop mode keeps reproducing the current track, unless it is changed using the player controls to go to the next/previous track. As in other applications, this is set by using the "Repeat" button, which now goes from "Off" -> "Repeat All" -> "Repeat One". --- player/player.go | 20 +++++++++++++++++++- ui/widgets/auxcontrols.go | 5 +++++ 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/player/player.go b/player/player.go index e9ad599..62f7091 100644 --- a/player/player.go +++ b/player/player.go @@ -58,12 +58,13 @@ type ReplayGainOptions struct { // Fallback gain intentionally omitted } -// The playback loop mode (LoopNone, LoopAll). +// The playback loop mode (LoopNone, LoopAll, LoopOne). type LoopMode int const ( LoopNone LoopMode = iota LoopAll + LoopOne ) // Information about a specific audio device. @@ -420,10 +421,23 @@ func (p *Player) SetLoopMode(mode LoopMode) error { if err := p.mpv.SetOptionString("loop-playlist", "no"); err != nil { return err } + if err := p.mpv.SetOptionString("loop-file", "no"); err != nil { + return err + } case LoopAll: if err := p.mpv.SetOptionString("loop-playlist", "inf"); err != nil { return err } + if err := p.mpv.SetOptionString("loop-file", "no"); err != nil { + return err + } + case LoopOne: + if err := p.mpv.SetOptionString("loop-playlist", "no"); err != nil { + return err + } + if err := p.mpv.SetOptionString("loop-file", "inf"); err != nil { + return err + } } p.loopMode = mode @@ -437,6 +451,8 @@ func (p *Player) SetNextLoopMode() error { case LoopNone: return p.SetLoopMode(LoopAll) case LoopAll: + return p.SetLoopMode(LoopOne) + case LoopOne: return p.SetLoopMode(LoopNone) default: return nil @@ -650,6 +666,8 @@ func (l LoopMode) String() string { 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 b110a66..85eacc9 100644 --- a/ui/widgets/auxcontrols.go +++ b/ui/widgets/auxcontrols.go @@ -68,8 +68,13 @@ func (a *AuxControls) OnChangeLoopMode(f func()) { func (a *AuxControls) SetLoopMode(mode string) { if mode == "all" { a.loop.Importance = widget.HighImportance + a.loop.Icon = theme.MediaReplayIcon() + } else if mode == "one" { + a.loop.Importance = widget.HighImportance + a.loop.Icon = theme.MediaReplayIcon() // TODO: This icon must be changed to the "Repeat" one with a 1. } else { a.loop.Importance = widget.MediumImportance + a.loop.Icon = theme.MediaReplayIcon() } a.loop.Refresh() } From a40ba5eb79043712576b25c156bb255ccc1a79e1 Mon Sep 17 00:00:00 2001 From: Michael Manganiello Date: Tue, 20 Jun 2023 23:51:04 -0300 Subject: [PATCH 2/2] Update icons to the new Repeat ones --- ui/theme/theme.go | 2 ++ ui/widgets/auxcontrols.go | 10 ++++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/ui/theme/theme.go b/ui/theme/theme.go index 8b2d484..889edd9 100644 --- a/ui/theme/theme.go +++ b/ui/theme/theme.go @@ -193,6 +193,8 @@ var ( ShuffleIcon fyne.Resource TracksIcon fyne.Resource FilterIcon fyne.Resource = theme.NewThemedResource(res.ResFilterSvg) + RepeatIcon fyne.Resource = theme.NewThemedResource(res.ResRepeatSvg) + RepeatOneIcon fyne.Resource = theme.NewThemedResource(res.ResRepeatoneSvg) ) // MUST be called at startup! diff --git a/ui/widgets/auxcontrols.go b/ui/widgets/auxcontrols.go index 85eacc9..0119e23 100644 --- a/ui/widgets/auxcontrols.go +++ b/ui/widgets/auxcontrols.go @@ -6,6 +6,8 @@ import ( "fyne.io/fyne/v2/layout" "fyne.io/fyne/v2/theme" "fyne.io/fyne/v2/widget" + + myTheme "github.com/dweymouth/supersonic/ui/theme" "github.com/dweymouth/supersonic/ui/util" ) @@ -41,7 +43,7 @@ func (b *miniButton) MinSize() fyne.Size { func NewAuxControls(initialVolume int) *AuxControls { a := &AuxControls{ VolumeControl: NewVolumeControl(initialVolume), - loop: newMiniButton(theme.MediaReplayIcon()), + loop: newMiniButton(myTheme.RepeatIcon), } a.container = container.NewHBox( layout.NewSpacer(), @@ -68,13 +70,13 @@ func (a *AuxControls) OnChangeLoopMode(f func()) { func (a *AuxControls) SetLoopMode(mode string) { if mode == "all" { a.loop.Importance = widget.HighImportance - a.loop.Icon = theme.MediaReplayIcon() + a.loop.Icon = myTheme.RepeatIcon } else if mode == "one" { a.loop.Importance = widget.HighImportance - a.loop.Icon = theme.MediaReplayIcon() // TODO: This icon must be changed to the "Repeat" one with a 1. + a.loop.Icon = myTheme.RepeatOneIcon } else { a.loop.Importance = widget.MediumImportance - a.loop.Icon = theme.MediaReplayIcon() + a.loop.Icon = myTheme.RepeatIcon } a.loop.Refresh() }