04a1f33cb1
- Full-screen Bubble Tea TUI with cream background fill using PadLine/FillBlankLines - Self-update command (--update) pulling from GitHub releases - install.sh for curl one-liner installation - Terminal Lovers section on web landing page with install command and CLI features - All 7 format categories, glob/directory batch support, auto-download ffmpeg
181 lines
3.9 KiB
Go
181 lines
3.9 KiB
Go
package theme
|
|
|
|
import (
|
|
"image/color"
|
|
"strings"
|
|
|
|
"charm.land/lipgloss/v2"
|
|
)
|
|
|
|
// ─── Pastel palette (matching the web app) ───────────────────
|
|
|
|
var (
|
|
Pink = lipgloss.Color("#f472b6")
|
|
Purple = lipgloss.Color("#a78bfa")
|
|
Blue = lipgloss.Color("#60a5fa")
|
|
Mint = lipgloss.Color("#34d399")
|
|
Orange = lipgloss.Color("#fb923c")
|
|
Teal = lipgloss.Color("#2dd4bf")
|
|
|
|
Cream = lipgloss.Color("#fdf6ef")
|
|
Warm = lipgloss.Color("#faf0e6")
|
|
Peach = lipgloss.Color("#fce8d5")
|
|
|
|
Dark = lipgloss.Color("#2d1f14")
|
|
Mid = lipgloss.Color("#8b7355")
|
|
Light = lipgloss.Color("#bfa98a")
|
|
|
|
Red = lipgloss.Color("#f43f5e")
|
|
DimBg = lipgloss.Color("#f6f6f6")
|
|
BorderCl = lipgloss.Color("#e8e0d4")
|
|
|
|
// Full-screen background
|
|
ScreenBg = lipgloss.Color("#fdf6ef") // Cream — matches the web app
|
|
)
|
|
|
|
// ─── Category colors ─────────────────────────────────────────
|
|
|
|
func CategoryColor(cat string) color.Color {
|
|
switch cat {
|
|
case "image":
|
|
return Pink
|
|
case "document":
|
|
return Blue
|
|
case "audio":
|
|
return Purple
|
|
case "video":
|
|
return Orange
|
|
case "data":
|
|
return Mint
|
|
case "font":
|
|
return Teal
|
|
case "spreadsheet":
|
|
return Mint
|
|
default:
|
|
return Light
|
|
}
|
|
}
|
|
|
|
// ─── Reusable styles ─────────────────────────────────────────
|
|
|
|
var (
|
|
// Title bar
|
|
TitleBar = lipgloss.NewStyle().
|
|
Bold(true).
|
|
Foreground(Dark).
|
|
Background(ScreenBg).
|
|
Padding(0, 2)
|
|
|
|
// Header / breadcrumb
|
|
Breadcrumb = lipgloss.NewStyle().
|
|
Foreground(Mid).
|
|
Bold(false)
|
|
|
|
BreadcrumbActive = lipgloss.NewStyle().
|
|
Foreground(Dark).
|
|
Bold(true)
|
|
|
|
// File row
|
|
FileName = lipgloss.NewStyle().
|
|
Foreground(Dark).
|
|
Bold(true)
|
|
|
|
FileSize = lipgloss.NewStyle().
|
|
Foreground(Light)
|
|
|
|
ExtBadge = func(c color.Color) lipgloss.Style {
|
|
return lipgloss.NewStyle().
|
|
Foreground(c).
|
|
Bold(true)
|
|
}
|
|
|
|
// Status indicators
|
|
StatusIdle = lipgloss.NewStyle().
|
|
Foreground(Light).
|
|
Italic(true)
|
|
|
|
StatusConverting = lipgloss.NewStyle().
|
|
Foreground(Pink).
|
|
Bold(true)
|
|
|
|
StatusDone = lipgloss.NewStyle().
|
|
Foreground(Mint).
|
|
Bold(true)
|
|
|
|
StatusError = lipgloss.NewStyle().
|
|
Foreground(Red).
|
|
Bold(true)
|
|
|
|
// Buttons / actions
|
|
ButtonPrimary = lipgloss.NewStyle().
|
|
Foreground(lipgloss.Color("#ffffff")).
|
|
Background(Pink).
|
|
Bold(true).
|
|
Padding(0, 2)
|
|
|
|
ButtonSecondary = lipgloss.NewStyle().
|
|
Foreground(lipgloss.Color("#ffffff")).
|
|
Background(Mint).
|
|
Bold(true).
|
|
Padding(0, 2)
|
|
|
|
// Progress bar
|
|
ProgressFilled = lipgloss.NewStyle().
|
|
Foreground(Pink)
|
|
|
|
ProgressEmpty = lipgloss.NewStyle().
|
|
Foreground(BorderCl)
|
|
|
|
// Help / footer
|
|
Help = lipgloss.NewStyle().
|
|
Foreground(Light).
|
|
Italic(true)
|
|
|
|
// Cursor / selection
|
|
Selected = lipgloss.NewStyle().
|
|
Bold(true).
|
|
Foreground(Pink)
|
|
|
|
Unselected = lipgloss.NewStyle().
|
|
Foreground(Dark)
|
|
|
|
// Divider
|
|
Divider = lipgloss.NewStyle().
|
|
Foreground(BorderCl)
|
|
|
|
// Logo / branding
|
|
Logo = lipgloss.NewStyle().
|
|
Foreground(Pink).
|
|
Bold(true)
|
|
)
|
|
|
|
// PadLine pads a single rendered line to the given width with the screen
|
|
// background color. This ensures every line carries the background color
|
|
// all the way to the right edge of the terminal.
|
|
func PadLine(line string, width int) string {
|
|
w := lipgloss.Width(line)
|
|
if w >= width {
|
|
return line
|
|
}
|
|
pad := lipgloss.NewStyle().
|
|
Background(ScreenBg).
|
|
Render(strings.Repeat(" ", width-w))
|
|
return line + pad
|
|
}
|
|
|
|
// FillBlankLines returns n blank lines fully painted with the screen
|
|
// background color at the given width.
|
|
func FillBlankLines(n, width int) string {
|
|
if n <= 0 {
|
|
return ""
|
|
}
|
|
blankLine := lipgloss.NewStyle().
|
|
Background(ScreenBg).
|
|
Render(strings.Repeat(" ", width))
|
|
lines := make([]string, n)
|
|
for i := range lines {
|
|
lines[i] = blankLine
|
|
}
|
|
return strings.Join(lines, "\n")
|
|
}
|