mirror of
https://github.com/charmbracelet/gum
synced 2024-05-10 02:06:36 +02:00
feat: Timeout for Choose Command (#384)
This commit is contained in:
parent
f73341a56c
commit
d1ad453ce6
|
@ -12,6 +12,9 @@ package choose
|
|||
|
||||
import (
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/charmbracelet/gum/timeout"
|
||||
|
||||
"github.com/charmbracelet/bubbles/paginator"
|
||||
tea "github.com/charmbracelet/bubbletea"
|
||||
|
@ -39,6 +42,8 @@ type model struct {
|
|||
headerStyle lipgloss.Style
|
||||
itemStyle lipgloss.Style
|
||||
selectedItemStyle lipgloss.Style
|
||||
hasTimeout bool
|
||||
timeout time.Duration
|
||||
}
|
||||
|
||||
type item struct {
|
||||
|
@ -47,13 +52,27 @@ type item struct {
|
|||
order int
|
||||
}
|
||||
|
||||
func (m model) Init() tea.Cmd { return nil }
|
||||
func (m model) Init() tea.Cmd {
|
||||
return timeout.Init(m.timeout, nil)
|
||||
}
|
||||
|
||||
func (m model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
|
||||
switch msg := msg.(type) {
|
||||
case tea.WindowSizeMsg:
|
||||
return m, nil
|
||||
|
||||
case timeout.TickTimeoutMsg:
|
||||
if msg.TimeoutValue <= 0 {
|
||||
m.quitting = true
|
||||
// If the user hasn't selected any items in a multi-select.
|
||||
// Then we select the item that they have pressed enter on. If they
|
||||
// have selected items, then we simply return them.
|
||||
if m.numSelected < 1 {
|
||||
m.items[m.index].selected = true
|
||||
}
|
||||
return m, tea.Quit
|
||||
}
|
||||
m.timeout = msg.TimeoutValue
|
||||
return m, timeout.Tick(msg.TimeoutValue, msg.Data)
|
||||
case tea.KeyMsg:
|
||||
start, end := m.paginator.GetSliceBounds(len(m.items))
|
||||
switch keypress := msg.String(); keypress {
|
||||
|
@ -151,6 +170,7 @@ func (m model) View() string {
|
|||
}
|
||||
|
||||
var s strings.Builder
|
||||
var timeoutStr string
|
||||
|
||||
start, end := m.paginator.GetSliceBounds(len(m.items))
|
||||
for i, item := range m.items[start:end] {
|
||||
|
@ -161,7 +181,10 @@ func (m model) View() string {
|
|||
}
|
||||
|
||||
if item.selected {
|
||||
s.WriteString(m.selectedItemStyle.Render(m.selectedPrefix + item.text))
|
||||
if m.hasTimeout {
|
||||
timeoutStr = timeout.Str(m.timeout)
|
||||
}
|
||||
s.WriteString(m.selectedItemStyle.Render(m.selectedPrefix + item.text + timeoutStr))
|
||||
} else if i == m.index%m.height {
|
||||
s.WriteString(m.cursorStyle.Render(m.cursorPrefix + item.text))
|
||||
} else {
|
||||
|
|
|
@ -112,6 +112,8 @@ func (o Options) Run() error {
|
|||
itemStyle: o.ItemStyle.ToLipgloss(),
|
||||
selectedItemStyle: o.SelectedItemStyle.ToLipgloss(),
|
||||
numSelected: currentSelected,
|
||||
hasTimeout: o.Timeout > 0,
|
||||
timeout: o.Timeout,
|
||||
}, tea.WithOutput(os.Stderr)).Run()
|
||||
|
||||
if err != nil {
|
||||
|
|
|
@ -1,23 +1,27 @@
|
|||
package choose
|
||||
|
||||
import "github.com/charmbracelet/gum/style"
|
||||
import (
|
||||
"time"
|
||||
|
||||
"github.com/charmbracelet/gum/style"
|
||||
)
|
||||
|
||||
// Options is the customization options for the choose command.
|
||||
type Options struct {
|
||||
Options []string `arg:"" optional:"" help:"Options to choose from."`
|
||||
|
||||
Limit int `help:"Maximum number of options to pick" default:"1" group:"Selection"`
|
||||
NoLimit bool `help:"Pick unlimited number of options (ignores limit)" group:"Selection"`
|
||||
Ordered bool `help:"Maintain the order of the selected options" env:"GUM_CHOOSE_ORDERED"`
|
||||
Height int `help:"Height of the list" default:"10" env:"GUM_CHOOSE_HEIGHT"`
|
||||
Cursor string `help:"Prefix to show on item that corresponds to the cursor position" default:"> " env:"GUM_CHOOSE_CURSOR"`
|
||||
Header string `help:"Header value" default:"" env:"GUM_CHOOSE_HEADER"`
|
||||
CursorPrefix string `help:"Prefix to show on the cursor item (hidden if limit is 1)" default:"○ " env:"GUM_CHOOSE_CURSOR_PREFIX"`
|
||||
SelectedPrefix string `help:"Prefix to show on selected items (hidden if limit is 1)" default:"◉ " env:"GUM_CHOOSE_SELECTED_PREFIX"`
|
||||
UnselectedPrefix string `help:"Prefix to show on unselected items (hidden if limit is 1)" default:"○ " env:"GUM_CHOOSE_UNSELECTED_PREFIX"`
|
||||
Selected []string `help:"Options that should start as selected" default:"" env:"GUM_CHOOSE_SELECTED"`
|
||||
CursorStyle style.Styles `embed:"" prefix:"cursor." set:"defaultForeground=212" envprefix:"GUM_CHOOSE_CURSOR_"`
|
||||
HeaderStyle style.Styles `embed:"" prefix:"header." set:"defaultForeground=240" envprefix:"GUM_CHOOSE_HEADER_"`
|
||||
ItemStyle style.Styles `embed:"" prefix:"item." hidden:"" envprefix:"GUM_CHOOSE_ITEM_"`
|
||||
SelectedItemStyle style.Styles `embed:"" prefix:"selected." set:"defaultForeground=212" envprefix:"GUM_CHOOSE_SELECTED_"`
|
||||
Options []string `arg:"" optional:"" help:"Options to choose from."`
|
||||
Limit int `help:"Maximum number of options to pick" default:"1" group:"Selection"`
|
||||
NoLimit bool `help:"Pick unlimited number of options (ignores limit)" group:"Selection"`
|
||||
Ordered bool `help:"Maintain the order of the selected options" env:"GUM_CHOOSE_ORDERED"`
|
||||
Height int `help:"Height of the list" default:"10" env:"GUM_CHOOSE_HEIGHT"`
|
||||
Cursor string `help:"Prefix to show on item that corresponds to the cursor position" default:"> " env:"GUM_CHOOSE_CURSOR"`
|
||||
Header string `help:"Header value" default:"" env:"GUM_CHOOSE_HEADER"`
|
||||
CursorPrefix string `help:"Prefix to show on the cursor item (hidden if limit is 1)" default:"○ " env:"GUM_CHOOSE_CURSOR_PREFIX"`
|
||||
SelectedPrefix string `help:"Prefix to show on selected items (hidden if limit is 1)" default:"◉ " env:"GUM_CHOOSE_SELECTED_PREFIX"`
|
||||
UnselectedPrefix string `help:"Prefix to show on unselected items (hidden if limit is 1)" default:"○ " env:"GUM_CHOOSE_UNSELECTED_PREFIX"`
|
||||
Selected []string `help:"Options that should start as selected" default:"" env:"GUM_CHOOSE_SELECTED"`
|
||||
CursorStyle style.Styles `embed:"" prefix:"cursor." set:"defaultForeground=212" envprefix:"GUM_CHOOSE_CURSOR_"`
|
||||
HeaderStyle style.Styles `embed:"" prefix:"header." set:"defaultForeground=240" envprefix:"GUM_CHOOSE_HEADER_"`
|
||||
ItemStyle style.Styles `embed:"" prefix:"item." hidden:"" envprefix:"GUM_CHOOSE_ITEM_"`
|
||||
SelectedItemStyle style.Styles `embed:"" prefix:"selected." set:"defaultForeground=212" envprefix:"GUM_CHOOSE_SELECTED_"`
|
||||
Timeout time.Duration `help:"Timeout until choose returns selected element" default:"0" env:"GUM_CCHOOSE_TIMEOUT"` // including timeout command options [Timeout,...]
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue