mirror of
https://github.com/zoriya/bubbles.git
synced 2026-08-16 01:43:21 +00:00
Merge branch 'master' into term/input
This commit is contained in:
@@ -20,7 +20,7 @@ jobs:
|
|||||||
|
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
- name: golangci-lint
|
- name: golangci-lint
|
||||||
uses: golangci/golangci-lint-action@v4
|
uses: golangci/golangci-lint-action@v5
|
||||||
with:
|
with:
|
||||||
# Optional: golangci-lint command line arguments.
|
# Optional: golangci-lint command line arguments.
|
||||||
args: --config .golangci-soft.yml --issues-exit-code=0
|
args: --config .golangci-soft.yml --issues-exit-code=0
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ jobs:
|
|||||||
|
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
- name: golangci-lint
|
- name: golangci-lint
|
||||||
uses: golangci/golangci-lint-action@v4
|
uses: golangci/golangci-lint-action@v5
|
||||||
with:
|
with:
|
||||||
# Optional: golangci-lint command line arguments.
|
# Optional: golangci-lint command line arguments.
|
||||||
#args:
|
#args:
|
||||||
|
|||||||
@@ -23,7 +23,6 @@ linters:
|
|||||||
- gomnd
|
- gomnd
|
||||||
- gomoddirectives
|
- gomoddirectives
|
||||||
- goprintffuncname
|
- goprintffuncname
|
||||||
- ifshort
|
|
||||||
# - lll
|
# - lll
|
||||||
- misspell
|
- misspell
|
||||||
- nakedret
|
- nakedret
|
||||||
|
|||||||
@@ -217,6 +217,8 @@ func (m Model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
|
|||||||
* [mritd/bubbles](https://github.com/mritd/bubbles): Some general-purpose
|
* [mritd/bubbles](https://github.com/mritd/bubbles): Some general-purpose
|
||||||
bubbles. Inputs with validation, menu selection, a modified progressbar, and
|
bubbles. Inputs with validation, menu selection, a modified progressbar, and
|
||||||
so on.
|
so on.
|
||||||
|
* [kevm/bubbleo](https://github.com/KevM/bubbleo): A set of bubbles with a
|
||||||
|
focus on navigation: navigation stacks, breakcrumbs, menus and so on.
|
||||||
* [treilik/bubbleboxer](https://github.com/treilik/bubbleboxer): Layout
|
* [treilik/bubbleboxer](https://github.com/treilik/bubbleboxer): Layout
|
||||||
multiple bubbles side-by-side in a layout-tree.
|
multiple bubbles side-by-side in a layout-tree.
|
||||||
* [treilik/bubblelister](https://github.com/treilik/bubblelister): An alternate
|
* [treilik/bubblelister](https://github.com/treilik/bubblelister): An alternate
|
||||||
|
|||||||
+30
-9
@@ -14,11 +14,12 @@ import (
|
|||||||
type Model struct {
|
type Model struct {
|
||||||
KeyMap KeyMap
|
KeyMap KeyMap
|
||||||
|
|
||||||
cols []Column
|
cols []Column
|
||||||
rows []Row
|
rows []Row
|
||||||
cursor int
|
cursor int
|
||||||
focus bool
|
focus bool
|
||||||
styles Styles
|
styles Styles
|
||||||
|
styleFunc StyleFunc
|
||||||
|
|
||||||
viewport viewport.Model
|
viewport viewport.Model
|
||||||
start int
|
start int
|
||||||
@@ -188,6 +189,13 @@ func WithStyles(s Styles) Option {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// WithStyleFunc sets the table style func which can determine a cell style per column, row, and selected state.
|
||||||
|
func WithStyleFunc(f StyleFunc) Option {
|
||||||
|
return func(m *Model) {
|
||||||
|
m.styleFunc = f
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// WithKeyMap sets the key map.
|
// WithKeyMap sets the key map.
|
||||||
func WithKeyMap(km KeyMap) Option {
|
func WithKeyMap(km KeyMap) Option {
|
||||||
return func(m *Model) {
|
return func(m *Model) {
|
||||||
@@ -397,6 +405,9 @@ func (m *Model) FromValues(value, separator string) {
|
|||||||
m.SetRows(rows)
|
m.SetRows(rows)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// StyleFunc is a function that can be used to customize the style of a table cell based on the row and column index.
|
||||||
|
type StyleFunc func(row, col int, value string) lipgloss.Style
|
||||||
|
|
||||||
func (m Model) headersView() string {
|
func (m Model) headersView() string {
|
||||||
var s = make([]string, 0, len(m.cols))
|
var s = make([]string, 0, len(m.cols))
|
||||||
for _, col := range m.cols {
|
for _, col := range m.cols {
|
||||||
@@ -410,20 +421,30 @@ func (m Model) headersView() string {
|
|||||||
return lipgloss.JoinHorizontal(lipgloss.Left, s...)
|
return lipgloss.JoinHorizontal(lipgloss.Left, s...)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *Model) renderRow(rowID int) string {
|
func (m *Model) renderRow(r int) string {
|
||||||
var s = make([]string, 0, len(m.cols))
|
var s = make([]string, 0, len(m.cols))
|
||||||
for i, value := range m.rows[rowID] {
|
for i, value := range m.rows[r] {
|
||||||
if m.cols[i].Width <= 0 {
|
if m.cols[i].Width <= 0 {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
var cellStyle lipgloss.Style
|
||||||
|
if m.styleFunc != nil {
|
||||||
|
cellStyle = m.styleFunc(r, i, value)
|
||||||
|
if r == m.cursor {
|
||||||
|
cellStyle.Inherit(m.styles.Selected)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
cellStyle = m.styles.Cell
|
||||||
|
}
|
||||||
|
|
||||||
style := lipgloss.NewStyle().Width(m.cols[i].Width).MaxWidth(m.cols[i].Width).Inline(true)
|
style := lipgloss.NewStyle().Width(m.cols[i].Width).MaxWidth(m.cols[i].Width).Inline(true)
|
||||||
renderedCell := m.styles.Cell.Render(style.Render(runewidth.Truncate(value, m.cols[i].Width, "…")))
|
renderedCell := cellStyle.Render(style.Render(runewidth.Truncate(value, m.cols[i].Width, "…")))
|
||||||
s = append(s, renderedCell)
|
s = append(s, renderedCell)
|
||||||
}
|
}
|
||||||
|
|
||||||
row := lipgloss.JoinHorizontal(lipgloss.Left, s...)
|
row := lipgloss.JoinHorizontal(lipgloss.Left, s...)
|
||||||
|
|
||||||
if rowID == m.cursor {
|
if r == m.cursor {
|
||||||
return m.styles.Selected.Render(row)
|
return m.styles.Selected.Render(row)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package table
|
package table
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/charmbracelet/lipgloss"
|
"github.com/charmbracelet/lipgloss"
|
||||||
@@ -108,3 +109,33 @@ func TestRenderRow(t *testing.T) {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func TestRenderRowStyleFunc(t *testing.T) {
|
||||||
|
tests := []struct {
|
||||||
|
name string
|
||||||
|
table *Model
|
||||||
|
expected string
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
name: "simple row",
|
||||||
|
table: &Model{
|
||||||
|
rows: []Row{{"Foooooo", "Baaaaar", "Baaaaaz"}},
|
||||||
|
cols: cols,
|
||||||
|
styleFunc: func(row, col int, value string) lipgloss.Style {
|
||||||
|
if strings.HasSuffix(value, "z") {
|
||||||
|
return lipgloss.NewStyle().Transform(strings.ToLower)
|
||||||
|
}
|
||||||
|
return lipgloss.NewStyle().Transform(strings.ToUpper)
|
||||||
|
},
|
||||||
|
},
|
||||||
|
expected: "FOOOOOO BAAAAAR baaaaaz ",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
for _, tc := range tests {
|
||||||
|
t.Run(tc.name, func(t *testing.T) {
|
||||||
|
row := tc.table.renderRow(0)
|
||||||
|
if row != tc.expected {
|
||||||
|
t.Fatalf("\n\nWant: \n%s\n\nGot: \n%s\n", tc.expected, row)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -0,0 +1,32 @@
|
|||||||
|
package textinput
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func Test_CurrentSuggestion(t *testing.T) {
|
||||||
|
textinput := New()
|
||||||
|
textinput.ShowSuggestions = true
|
||||||
|
|
||||||
|
suggestion := textinput.CurrentSuggestion()
|
||||||
|
expected := ""
|
||||||
|
if suggestion != expected {
|
||||||
|
t.Fatalf("Error: expected no current suggestion but was %s", suggestion)
|
||||||
|
}
|
||||||
|
|
||||||
|
textinput.SetSuggestions([]string{"test1", "test2", "test3"})
|
||||||
|
suggestion = textinput.CurrentSuggestion()
|
||||||
|
expected = ""
|
||||||
|
if suggestion != expected {
|
||||||
|
t.Fatalf("Error: expected no current suggestion but was %s", suggestion)
|
||||||
|
}
|
||||||
|
|
||||||
|
textinput.SetValue("test")
|
||||||
|
textinput.updateSuggestions()
|
||||||
|
textinput.nextSuggestion()
|
||||||
|
suggestion = textinput.CurrentSuggestion()
|
||||||
|
expected = "test2"
|
||||||
|
if suggestion != expected {
|
||||||
|
t.Fatalf("Error: expected first suggestion but was %s", suggestion)
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user