♻️ I think I'm finally happy with the Spinner implementation

This commit is contained in:
Dan Jones 2024-10-25 13:17:35 -05:00
commit 2552adbd3e

View file

@ -58,28 +58,47 @@ func (m model) View() string {
return str return str
} }
func Spin(ctx context.Context, message string) (chan string, chan error) { type Spinner interface {
p := tea.NewProgram(newModel(message), tea.WithContext(ctx)) Wait() error
SetMessage(string)
msgChan := make(chan string, 10) Err() error
errChan := make(chan error) }
go func() { var _ Spinner = new(spin)
for {
m := <-msgChan type spin struct {
p.Send(textMessage(m)) p *tea.Program
} err error
}() finished chan struct{}
go func() { }
_, err := p.Run()
if errors.Is(err, context.Canceled) { func (s *spin) Wait() error {
err = nil <-s.finished
} else if errors.Is(err, context.DeadlineExceeded) { return s.Err()
err = nil }
} else if errors.Is(err, tea.ErrProgramKilled) {
err = nil func (s *spin) SetMessage(msg string) {
} s.p.Send(textMessage(msg))
errChan <- err }
}()
return msgChan, errChan func (s *spin) Err() error {
if errors.Is(s.err, context.Canceled) {
return nil
} else if errors.Is(s.err, context.DeadlineExceeded) {
return nil
} else if errors.Is(s.err, tea.ErrProgramKilled) {
return nil
}
return s.err
}
func Spin(ctx context.Context, message string) Spinner {
p := tea.NewProgram(newModel(message), tea.WithContext(ctx))
s := &spin{p: p, finished: make(chan struct{}, 1)}
go func() {
_, err := s.p.Run()
s.err = err
s.finished <- struct{}{}
}()
return s
} }