table

package
v0.36.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: May 25, 2026 License: MIT Imports: 6 Imported by: 0

README

Table

Column-aligned data table with sortable headers, keyboard navigation, internal scrolling, and optional row selection.

table preview

Install

glyph add table

This copies table.go (and its test file) into your repo at the path your glyph.json aliases declare. After install, the file is yours: edit it, refactor it, rename it. There is no table library to keep in sync.

Hello, world

package main

import (
	"fmt"

	"github.com/truffle-dev/glyph/components/table"
)

func main() {
	t := table.New().
		WithColumns(
			table.Column{Key: "repo", Title: "Repo", Sortable: true},
			table.Column{Key: "owner", Title: "Owner", Sortable: true},
			table.Column{Key: "stars", Title: "Stars", Align: table.AlignRight, Sortable: true},
		).
		WithRows(
			table.Row{Cells: []string{"glyph", "truffle-dev", "12"}, Value: "glyph"},
			table.Row{Cells: []string{"vigil", "baudsmithstudios", "47"}, Value: "vigil"},
			table.Row{Cells: []string{"voltagent", "VoltAgent", "284"}, Value: "voltagent"},
		).
		WithSize(60, 8).
		WithRowSelection(true)
	fmt.Println(t.View())
}

API surface

Package: table

Types

  • Column
  • Row
  • Align
  • Model
  • SelectMsg
  • SortMsg
  • CursorMsg

Functions and methods

  • New
  • WithColumns
  • WithRows
  • WithSize
  • WithSelectedRow
  • WithSortBy
  • WithRowSelection
  • WithHighlightCursor
  • WithTheme
  • Cursor
  • SelectedRow
  • SortBy
  • Rows
  • Columns
  • Init
  • Update
  • View

Dependencies

  • glyph component theme (installed automatically)
  • github.com/charmbracelet/bubbletea@v1.3.10
  • github.com/charmbracelet/lipgloss@v1.1.0

Notes

Up/Down or j/k move the cursor; Left/Right or h/l shift the "active" column underline; s toggles ascending/descending sort on the active column (only when Sortable: true); PgUp/PgDn page; Home/g and End/G jump to the ends; Enter emits table.SelectMsg{Row, Index} when WithRowSelection(true). Columns with Width: 0 auto-fit to the widest cell (capped at 40 cells with a 2-cell padding); overflow is absorbed by proportional shrink of auto columns first, then right-truncation of fixed columns with an ellipsis. Sort comparison is numeric when both cells parse as floats, otherwise byte-wise lex; empties sort last in ascending and first in descending; sort is stable so equal keys keep insertion order.

See also

License

MIT, same as the rest of glyph.

Documentation

Overview

Package table renders a column-aligned data grid with sortable headers, keyboard navigation, internal scrolling, and optional row selection. It's the primitive every operator surface reaches for once a list outgrows a single column: a queue of jobs with status and owner, a roster of repos with engagement counts, a sweep of PRs with CI state.

A table owns the cursor, the scroll window, the active sort column, and an optional "active" header used to steer the next sort. It does not own the detail view. The parent reads SelectedRow() to drive the panel beside the table, and listens for SelectMsg on Enter when row selection is enabled.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Align

type Align int

Align controls horizontal alignment of a column's cells. AlignLeft is the default and is what string-flavored columns want; AlignRight is what numeric columns want; AlignCenter is for narrow status badges.

const (
	AlignLeft Align = iota
	AlignRight
	AlignCenter
)

type Column

type Column struct {
	Key      string
	Title    string
	Width    int
	Align    Align
	Sortable bool
}

Column describes one vertical column of the table. Width == 0 means auto-fit to the widest content seen across rows (capped at 40 cells) and the title. Otherwise Width is treated as the fixed render width in cells.

type CursorMsg

type CursorMsg struct {
	Index int
}

CursorMsg is emitted on cursor movement. The parent can ignore it; it exists for surfaces that mirror the cursor in a separate detail pane.

type Model

type Model struct {
	// contains filtered or unexported fields
}

Model is the table's Bubble Tea model. Construct with New and chain builder calls; every method returns a new Model.

func New

func New() Model

New constructs an empty table with safe defaults: cursor highlight on, no row selection, a generous 80x12 render box.

func (Model) Columns

func (m Model) Columns() []Column

Columns returns the column set (copy).

func (Model) Cursor

func (m Model) Cursor() int

Cursor returns the current cursor index, or 0 if there are no rows.

func (Model) Init

func (m Model) Init() tea.Cmd

Init implements tea.Model.

func (Model) Rows

func (m Model) Rows() []Row

Rows returns the row set in current sorted order (copy).

func (Model) SelectedRow

func (m Model) SelectedRow() (Row, bool)

SelectedRow returns the row under the cursor. Bool is false on empty.

func (Model) SortBy

func (m Model) SortBy() (string, bool)

SortBy returns the current sort key and direction. Empty key means no active sort.

func (Model) Update

func (m Model) Update(msg tea.Msg) (Model, tea.Cmd)

Update routes key and resize messages. Returns (Model, tea.Cmd) to match the convention of every other glyph component; the table value is also a tea.Model so callers can pass it through tea.Program.

func (Model) View

func (m Model) View() string

View renders the header, separator, and visible window of rows. An empty row set produces header + separator + a placeholder line.

func (Model) WithColumns

func (m Model) WithColumns(cols ...Column) Model

WithColumns replaces the column set. The active sort column is cleared if the previous sort key no longer matches any column.

func (Model) WithHighlightCursor

func (m Model) WithHighlightCursor(enabled bool) Model

WithHighlightCursor toggles the surface highlight applied to the row under the cursor. Default true.

func (Model) WithRowSelection

func (m Model) WithRowSelection(enabled bool) Model

WithRowSelection toggles Enter-emits-SelectMsg behavior.

func (Model) WithRows

func (m Model) WithRows(rows ...Row) Model

WithRows replaces the row set. Cursor clamps to the new length; the active sort (if any) is re-applied so callers can hand in unsorted data and trust the view.

func (Model) WithSelectedRow

func (m Model) WithSelectedRow(index int) Model

WithSelectedRow positions the cursor. Clamped to [0, len(rows)).

func (Model) WithSize

func (m Model) WithSize(width, height int) Model

WithSize sets the render width and total height. Height includes the header row plus one separator line, so visible-row count is height-2.

func (Model) WithSortBy

func (m Model) WithSortBy(columnKey string, descending bool) Model

WithSortBy sets the active sort column by key and direction. Pass columnKey == "" to clear the sort. Applies a stable sort immediately.

func (Model) WithTheme

func (m Model) WithTheme(t theme.Theme) Model

WithTheme overrides the palette. Not part of the required API surface but useful for stories that swap Light/Dark; kept unexported-of-spec would force a fork, so it's exported.

type Row

type Row struct {
	Cells []string
	Value any
}

Row is one record. Cells must line up with Columns by index; missing trailing cells render as blank. Value is opaque payload the parent can read off SelectedRow() or pull off SelectMsg.

type SelectMsg

type SelectMsg struct {
	Row   Row
	Index int
}

SelectMsg is emitted on Enter when row selection is enabled.

type SortMsg

type SortMsg struct {
	ColumnKey  string
	Descending bool
}

SortMsg is emitted when the active sort changes (either via WithSortBy or pressing 's' over a sortable column).

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL