fix(tui): rework lists and search dialog

This commit is contained in:
adamdotdevin
2025-07-15 08:07:20 -05:00
parent b5c85d3806
commit 533f64fe26
16 changed files with 579 additions and 972 deletions

View File

@@ -5,6 +5,7 @@ import (
list "github.com/sst/opencode/internal/components/list"
"github.com/sst/opencode/internal/components/modal"
"github.com/sst/opencode/internal/layout"
"github.com/sst/opencode/internal/styles"
"github.com/sst/opencode/internal/theme"
"github.com/sst/opencode/internal/util"
)
@@ -24,7 +25,7 @@ type themeDialog struct {
height int
modal *modal.Modal
list list.List[list.StringItem]
list list.List[list.Item]
originalTheme string
themeApplied bool
}
@@ -42,16 +43,18 @@ func (t *themeDialog) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
switch msg.String() {
case "enter":
if item, idx := t.list.GetSelectedItem(); idx >= 0 {
selectedTheme := string(item)
if err := theme.SetTheme(selectedTheme); err != nil {
// status.Error(err.Error())
return t, nil
if stringItem, ok := item.(list.StringItem); ok {
selectedTheme := string(stringItem)
if err := theme.SetTheme(selectedTheme); err != nil {
// status.Error(err.Error())
return t, nil
}
t.themeApplied = true
return t, tea.Sequence(
util.CmdHandler(modal.CloseModalMsg{}),
util.CmdHandler(ThemeSelectedMsg{ThemeName: selectedTheme}),
)
}
t.themeApplied = true
return t, tea.Sequence(
util.CmdHandler(modal.CloseModalMsg{}),
util.CmdHandler(ThemeSelectedMsg{ThemeName: selectedTheme}),
)
}
}
@@ -61,11 +64,13 @@ func (t *themeDialog) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
var cmd tea.Cmd
listModel, cmd := t.list.Update(msg)
t.list = listModel.(list.List[list.StringItem])
t.list = listModel.(list.List[list.Item])
if item, newIdx := t.list.GetSelectedItem(); newIdx >= 0 && newIdx != prevIdx {
theme.SetTheme(string(item))
return t, util.CmdHandler(ThemeSelectedMsg{ThemeName: string(item)})
if stringItem, ok := item.(list.StringItem); ok {
theme.SetTheme(string(stringItem))
return t, util.CmdHandler(ThemeSelectedMsg{ThemeName: string(stringItem)})
}
}
return t, cmd
}
@@ -94,21 +99,32 @@ func NewThemeDialog() ThemeDialog {
}
}
list := list.NewStringList(
themes,
10, // maxVisibleThemes
"No themes available",
true,
// Convert themes to list items
items := make([]list.Item, len(themes))
for i, theme := range themes {
items[i] = list.StringItem(theme)
}
listComponent := list.NewListComponent(
list.WithItems(items),
list.WithMaxVisibleHeight[list.Item](10),
list.WithFallbackMessage[list.Item]("No themes available"),
list.WithAlphaNumericKeys[list.Item](true),
list.WithRenderFunc(func(item list.Item, selected bool, width int, baseStyle styles.Style) string {
return item.Render(selected, width, baseStyle)
}),
list.WithSelectableFunc(func(item list.Item) bool {
return item.Selectable()
}),
)
// Set the initial selection to the current theme
list.SetSelectedIndex(selectedIdx)
listComponent.SetSelectedIndex(selectedIdx)
// Set the max width for the list to match the modal width
list.SetMaxWidth(36) // 40 (modal max width) - 4 (modal padding)
listComponent.SetMaxWidth(36) // 40 (modal max width) - 4 (modal padding)
return &themeDialog{
list: list,
list: listComponent,
modal: modal.New(modal.WithTitle("Select Theme"), modal.WithMaxWidth(40)),
originalTheme: currentTheme,
themeApplied: false,