feat: add a Styler interface for styling bubbles

This change introduces a Styler interface that allows users to define
custom styles for bubbles. The interface is implemented by the StylerFunc
type, which is a function type that takes a boolean argument and returns
a value of any type.

This allows a user to define a custom StylerFunc that returns a custom
style for a bubble based on the background color of the terminal.
This commit is contained in:
Ayman Bagabas
2024-10-29 15:54:40 -04:00
parent db64e3cd78
commit 8fdc81c836
8 changed files with 34 additions and 33 deletions
+4 -6
View File
@@ -94,16 +94,14 @@ type DefaultDelegate struct {
}
// NewDefaultDelegate creates a new delegate with default styles.
func NewDefaultDelegate() DefaultDelegate {
func NewDefaultDelegate(isDark bool) DefaultDelegate {
const defaultHeight = 2
const defaultSpacing = 1
return DefaultDelegate{
ShowDescription: true,
// XXX: Let the user choose between light and dark colors. We've
// temporarily hardcoded the dark colors here.
Styles: NewDefaultItemStyles(true),
height: defaultHeight,
spacing: defaultSpacing,
Styles: NewDefaultItemStyles(isDark),
height: defaultHeight,
spacing: defaultSpacing,
}
}
+3 -5
View File
@@ -196,10 +196,8 @@ type Model struct {
}
// New returns a new model with sensible defaults.
func New(items []Item, delegate ItemDelegate, width, height int) Model {
// XXX: Let the user choose between light and dark colors. We've
// temporarily hardcoded the dark colors here.
styles := DefaultStyles(true)
func New(items []Item, delegate ItemDelegate, width, height int, isDark bool) Model {
styles := DefaultStyles(isDark)
sp := spinner.New()
sp.Spinner = spinner.Line
@@ -239,7 +237,7 @@ func New(items []Item, delegate ItemDelegate, width, height int) Model {
items: items,
Paginator: p,
spinner: sp,
Help: help.New(),
Help: help.New(isDark),
}
m.updatePagination()
+5 -5
View File
@@ -30,7 +30,7 @@ func (d itemDelegate) Render(w io.Writer, m Model, index int, listItem Item) {
}
func TestStatusBarItemName(t *testing.T) {
list := New([]Item{item("foo"), item("bar")}, itemDelegate{}, 10, 10)
list := New([]Item{item("foo"), item("bar")}, itemDelegate{}, 10, 10, true)
expected := "2 items"
if !strings.Contains(list.statusView(), expected) {
t.Fatalf("Error: expected view to contain %s", expected)
@@ -44,7 +44,7 @@ func TestStatusBarItemName(t *testing.T) {
}
func TestStatusBarWithoutItems(t *testing.T) {
list := New([]Item{}, itemDelegate{}, 10, 10)
list := New([]Item{}, itemDelegate{}, 10, 10, true)
expected := "No items"
if !strings.Contains(list.statusView(), expected) {
@@ -53,7 +53,7 @@ func TestStatusBarWithoutItems(t *testing.T) {
}
func TestCustomStatusBarItemName(t *testing.T) {
list := New([]Item{item("foo"), item("bar")}, itemDelegate{}, 10, 10)
list := New([]Item{item("foo"), item("bar")}, itemDelegate{}, 10, 10, true)
list.SetStatusBarItemName("connection", "connections")
expected := "2 connections"
@@ -77,7 +77,7 @@ func TestCustomStatusBarItemName(t *testing.T) {
func TestSetFilterText(t *testing.T) {
tc := []Item{item("foo"), item("bar"), item("baz")}
list := New(tc, itemDelegate{}, 10, 10)
list := New(tc, itemDelegate{}, 10, 10, true)
list.SetFilterText("ba")
list.SetFilterState(Unfiltered)
@@ -102,7 +102,7 @@ func TestSetFilterText(t *testing.T) {
func TestSetFilterState(t *testing.T) {
tc := []Item{item("foo"), item("bar"), item("baz")}
list := New(tc, itemDelegate{}, 10, 10)
list := New(tc, itemDelegate{}, 10, 10, true)
list.SetFilterText("ba")
list.SetFilterState(Unfiltered)