1package tui
2
3import (
4 "fmt"
5 "strings"
6
7 tea "github.com/charmbracelet/bubbletea"
8 "github.com/charmbracelet/lipgloss"
9 "github.com/floatpane/matcha/config"
10)
11
12// Styles defined locally to avoid import issues.
13var (
14 docStyle = lipgloss.NewStyle().Margin(1, 2)
15 titleStyle = lipgloss.NewStyle().Foreground(lipgloss.Color("#FFFDF5")).Background(lipgloss.Color("#25A065")).Padding(0, 1)
16 listHeader = lipgloss.NewStyle().Foreground(lipgloss.Color("241")).PaddingBottom(1)
17 itemStyle = lipgloss.NewStyle().PaddingLeft(2)
18 selectedItemStyle = lipgloss.NewStyle().PaddingLeft(2).Foreground(lipgloss.Color("42"))
19)
20
21type Choice struct {
22 cursor int
23 choices []string
24 hasCachedDraft bool
25 hasSavedDrafts bool
26}
27
28func NewChoice(hasCachedDraft bool) Choice {
29 hasSavedDrafts := config.HasDrafts()
30 choices := []string{"View Inbox", "Compose Email"}
31 if hasSavedDrafts {
32 choices = append(choices, "Drafts")
33 }
34 choices = append(choices, "Settings")
35 if hasCachedDraft {
36 choices = append(choices, "Restore Draft")
37 }
38 return Choice{
39 choices: choices,
40 hasCachedDraft: hasCachedDraft,
41 hasSavedDrafts: hasSavedDrafts,
42 }
43}
44
45func (m Choice) Init() tea.Cmd {
46 return nil
47}
48
49func (m Choice) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
50 switch msg := msg.(type) {
51 case tea.KeyMsg:
52 switch msg.String() {
53 case "up", "k":
54 if m.cursor > 0 {
55 m.cursor--
56 }
57 case "down", "j":
58 if m.cursor < len(m.choices)-1 {
59 m.cursor++
60 }
61 case "enter":
62 selectedChoice := m.choices[m.cursor]
63 switch selectedChoice {
64 case "View Inbox":
65 return m, func() tea.Msg { return GoToInboxMsg{} }
66 case "Compose Email":
67 return m, func() tea.Msg { return GoToSendMsg{} }
68 case "Drafts":
69 return m, func() tea.Msg { return GoToDraftsMsg{} }
70 case "Settings":
71 return m, func() tea.Msg { return GoToSettingsMsg{} }
72 case "Restore Draft":
73 return m, func() tea.Msg { return RestoreDraftMsg{} }
74 }
75 }
76 }
77 return m, nil
78}
79
80func (m Choice) View() string {
81 var b strings.Builder
82
83 b.WriteString(titleStyle.Render("Matcha") + "\n\n")
84 b.WriteString(listHeader.Render("What would you like to do?"))
85 b.WriteString("\n\n")
86
87 for i, choice := range m.choices {
88 if m.cursor == i {
89 b.WriteString(selectedItemStyle.Render(fmt.Sprintf("> %s", choice)))
90 } else {
91 b.WriteString(itemStyle.Render(fmt.Sprintf(" %s", choice)))
92 }
93 b.WriteString("\n")
94 }
95
96 b.WriteString("\n\n")
97 b.WriteString(helpStyle.Render("Use ↑/↓ to navigate, enter to select, and ctrl+c to quit."))
98
99 return docStyle.Render(b.String())
100}