1package statusbar
  2
  3import (
  4	tea "github.com/charmbracelet/bubbletea"
  5	"github.com/charmbracelet/lipgloss"
  6	"github.com/charmbracelet/soft-serve/ui/common"
  7	"github.com/muesli/reflow/truncate"
  8)
  9
 10// StatusBarMsg is a message sent to the status bar.
 11type StatusBarMsg struct {
 12	Key    string
 13	Value  string
 14	Info   string
 15	Branch string
 16}
 17
 18// StatusBar is a status bar model.
 19type StatusBar struct {
 20	common common.Common
 21	msg    StatusBarMsg
 22}
 23
 24// Model is an interface that supports setting the status bar information.
 25type Model interface {
 26	StatusBarValue() string
 27	StatusBarInfo() string
 28}
 29
 30// New creates a new status bar component.
 31func New(c common.Common) *StatusBar {
 32	s := &StatusBar{
 33		common: c,
 34	}
 35	return s
 36}
 37
 38// SetSize implements common.Component.
 39func (s *StatusBar) SetSize(width, height int) {
 40	s.common.Width = width
 41	s.common.Height = height
 42}
 43
 44// Init implements tea.Model.
 45func (s *StatusBar) Init() tea.Cmd {
 46	return nil
 47}
 48
 49// Update implements tea.Model.
 50func (s *StatusBar) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
 51	switch msg := msg.(type) {
 52	case StatusBarMsg:
 53		s.msg = msg
 54	}
 55	return s, nil
 56}
 57
 58// View implements tea.Model.
 59func (s *StatusBar) View() string {
 60	st := s.common.Styles
 61	w := lipgloss.Width
 62	help := s.common.Zone.Mark(
 63		"repo-help",
 64		st.StatusBarHelp.Render("? Help"),
 65	)
 66	key := st.StatusBarKey.Render(s.msg.Key)
 67	info := ""
 68	if s.msg.Info != "" {
 69		info = st.StatusBarInfo.Render(s.msg.Info)
 70	}
 71	branch := st.StatusBarBranch.Render(s.msg.Branch)
 72	maxWidth := s.common.Width - w(key) - w(info) - w(branch) - w(help)
 73	v := truncate.StringWithTail(s.msg.Value, uint(maxWidth-st.StatusBarValue.GetHorizontalFrameSize()), "…")
 74	value := st.StatusBarValue.
 75		Width(maxWidth).
 76		Render(v)
 77
 78	return lipgloss.NewStyle().MaxWidth(s.common.Width).
 79		Render(
 80			lipgloss.JoinHorizontal(lipgloss.Top,
 81				key,
 82				value,
 83				info,
 84				branch,
 85				help,
 86			),
 87		)
 88}
 89
 90// StatusBarCmd returns a command that sets the status bar information.
 91func StatusBarCmd(key, value, info, branch string) tea.Cmd {
 92	return func() tea.Msg {
 93		return StatusBarMsg{
 94			Key:    key,
 95			Value:  value,
 96			Info:   info,
 97			Branch: branch,
 98		}
 99	}
100}