1package dialog
2
3import (
4 "strings"
5
6 "github.com/charmbracelet/crush/internal/ui/list"
7 "github.com/charmbracelet/crush/internal/ui/styles"
8 "github.com/sahilm/fuzzy"
9)
10
11// CommandItem wraps a uicmd.Command to implement the ListItem interface.
12type CommandItem struct {
13 *list.Versioned
14 id string
15 title string
16 shortcut string
17 action Action
18 aliases []string
19 t *styles.Styles
20 m fuzzy.Match
21 cache map[int]string
22 focused bool
23}
24
25var _ ListItem = &CommandItem{Versioned: list.NewVersioned()}
26
27// NewCommandItem creates a new CommandItem.
28func NewCommandItem(t *styles.Styles, id, title, shortcut string, action Action) *CommandItem {
29 return &CommandItem{
30 Versioned: list.NewVersioned(),
31 id: id,
32 t: t,
33 title: title,
34 shortcut: shortcut,
35 action: action,
36 }
37}
38
39// Finished implements list.Item. Command items are render-stable
40// outside of explicit SetFocused / SetMatch.
41func (c *CommandItem) Finished() bool {
42 return true
43}
44
45// WithAliases returns the CommandItem with the given aliases for filtering.
46func (c *CommandItem) WithAliases(aliases ...string) *CommandItem {
47 c.aliases = aliases
48 return c
49}
50
51// Filter implements ListItem.
52func (c *CommandItem) Filter() string {
53 if len(c.aliases) == 0 {
54 return c.title
55 }
56 return c.title + " " + strings.Join(c.aliases, " ")
57}
58
59// ID implements ListItem.
60func (c *CommandItem) ID() string {
61 return c.id
62}
63
64// SetFocused implements ListItem.
65func (c *CommandItem) SetFocused(focused bool) {
66 if c.focused == focused {
67 return
68 }
69 c.cache = nil
70 c.focused = focused
71 if c.Versioned != nil {
72 c.Bump()
73 }
74}
75
76// SetMatch implements ListItem.
77func (c *CommandItem) SetMatch(m fuzzy.Match) {
78 if sameFuzzyMatch(c.m, m) {
79 return
80 }
81 c.cache = nil
82 c.m = m
83 if c.Versioned != nil {
84 c.Bump()
85 }
86}
87
88// Action returns the action associated with the command item.
89func (c *CommandItem) Action() Action {
90 return c.action
91}
92
93// Shortcut returns the shortcut associated with the command item.
94func (c *CommandItem) Shortcut() string {
95 return c.shortcut
96}
97
98// Render implements ListItem.
99func (c *CommandItem) Render(width int) string {
100 styles := ListItemStyles{
101 ItemBlurred: c.t.Dialog.NormalItem,
102 ItemFocused: c.t.Dialog.SelectedItem,
103 InfoTextBlurred: c.t.Dialog.ListItem.InfoBlurred,
104 InfoTextFocused: c.t.Dialog.ListItem.InfoFocused,
105 }
106 return renderItem(styles, c.title, c.shortcut, c.focused, width, c.cache, &c.m)
107}