From 09feddcc61e950dc2bdbf199dd4edafa6ea2136e Mon Sep 17 00:00:00 2001 From: Maas Lalani Date: Wed, 6 Jul 2022 12:09:35 -0400 Subject: [PATCH] feat: Add `gum style` command MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Style provides a shell script interface for Lip Gloss. It allows you to use Lip Gloss to style text without needing to use Go. All of the styling options are available as flags. Let's make some text glamorous using bash: ``` gum style \ --foreground "#FF06B7" --border "double" \ --margin 2 --padding "2 4" --width 50 \ "And oh gosh, how delicious the fabulous frizzy frobscottle" \ "was! It was sweet and refreshing. It tasted of vanilla and" \ "cream, with just the faintest trace of raspberries on the" \ "edge of the flavour. And the bubbles were wonderful." ``` Output: ``` ╔══════════════════════════════════════════════════╗ ║ ║ ║ ║ ║ And oh gosh, how delicious the fabulous ║ ║ frizzy frobscottle was It was sweet and ║ ║ refreshing. It tasted of vanilla and ║ ║ cream, with just the faintest trace of ║ ║ raspberries on the edge of the flavour. ║ ║ And the bubbles were wonderful. ║ ║ ║ ║ ║ ╚══════════════════════════════════════════════════╝ ``` --- style/align.go | 12 ++++++++++++ style/borders.go | 13 +++++++++++++ style/command.go | 28 ++++++++++++++++++++++++++++ style/options.go | 21 +++++++++++++++++++++ style/spacing.go | 41 +++++++++++++++++++++++++++++++++++++++++ style/style.go | 1 + 6 files changed, 116 insertions(+) create mode 100644 style/align.go create mode 100644 style/borders.go create mode 100644 style/command.go create mode 100644 style/options.go create mode 100644 style/spacing.go create mode 100644 style/style.go diff --git a/style/align.go b/style/align.go new file mode 100644 index 0000000..f94f77e --- /dev/null +++ b/style/align.go @@ -0,0 +1,12 @@ +package style + +import "github.com/charmbracelet/lipgloss" + +// align maps strings to `lipgloss.Position`s +var align = map[string]lipgloss.Position{ + "center": lipgloss.Center, + "left": lipgloss.Left, + "top": lipgloss.Top, + "bottom": lipgloss.Bottom, + "right": lipgloss.Right, +} diff --git a/style/borders.go b/style/borders.go new file mode 100644 index 0000000..8ce177f --- /dev/null +++ b/style/borders.go @@ -0,0 +1,13 @@ +package style + +import "github.com/charmbracelet/lipgloss" + +// border maps strings to `lipgloss.Border`s +var border map[string]lipgloss.Border = map[string]lipgloss.Border{ + "double": lipgloss.DoubleBorder(), + "hidden": lipgloss.HiddenBorder(), + "none": {}, + "normal": lipgloss.NormalBorder(), + "rounded": lipgloss.RoundedBorder(), + "thick": lipgloss.ThickBorder(), +} diff --git a/style/command.go b/style/command.go new file mode 100644 index 0000000..8944fd4 --- /dev/null +++ b/style/command.go @@ -0,0 +1,28 @@ +package style + +import ( + "fmt" + + "github.com/charmbracelet/lipgloss" +) + +// Run provides a shell script interface for the Lip Gloss styling. +// https://github.com/charmbracelet/lipgloss +func (o Options) Run() { + fmt.Println(lipgloss.NewStyle(). + Foreground(lipgloss.Color(o.Foreground)). + Background(lipgloss.Color(o.Background)). + BorderBackground(lipgloss.Color(o.BorderBackground)). + BorderForeground(lipgloss.Color(o.BorderForeground)). + Align(align[o.Align]). + Bold(o.Bold). + Border(border[o.Border]). + Margin(parseMargin(o.Margin)). + Padding(parsePadding(o.Padding)). + Height(o.Height). + Width(o.Width). + Faint(o.Faint). + Italic(o.Italic). + Strikethrough(o.Strikethrough). + Render(o.Text)) +} diff --git a/style/options.go b/style/options.go new file mode 100644 index 0000000..14c14fc --- /dev/null +++ b/style/options.go @@ -0,0 +1,21 @@ +package style + +// Options is the customization options for the style command. +type Options struct { + Text string `arg:"" optional:"" help:"Text to style"` + + Background string `help:"Background color"` + Foreground string `help:"Foreground color"` + BorderBackground string `help:"Border background color"` + BorderForeground string `help:"Border foreground color"` + Align string `help:"Text alignment" enum:"left,center,right,bottom,middle,top" default:"left"` + Border string `help:"Border style to apply" enum:"none,hidden,normal,rounded,thick,double" default:"none"` + Height int `help:"Height of output"` + Width int `help:"Width of output"` + Margin string `help:"Margin to apply around the text."` + Padding string `help:"Padding to apply around the text."` + Bold bool `help:"Apply bold formatting"` + Faint bool `help:"Apply faint formatting"` + Italic bool `help:"Apply italic formatting"` + Strikethrough bool `help:"Apply strikethrough formatting"` +} diff --git a/style/spacing.go b/style/spacing.go new file mode 100644 index 0000000..0c8e4bb --- /dev/null +++ b/style/spacing.go @@ -0,0 +1,41 @@ +package style + +import ( + "strconv" + "strings" +) + +// parsePadding parses 1 - 4 integers from a string and returns them in a top, +// right, bottom, left order for use in the lipgloss.Padding() method +func parsePadding(s string) (int, int, int, int) { + var ints []int + + tokens := strings.Split(s, " ") + + // All tokens must be an integer + for _, token := range tokens { + parsed, err := strconv.Atoi(token) + if err != nil { + return 0, 0, 0, 0 + } + ints = append(ints, parsed) + } + + if len(tokens) == 1 { + return ints[0], ints[0], ints[0], ints[0] + } + + if len(tokens) == 2 { + return ints[0], ints[1], ints[0], ints[1] + } + + if len(tokens) == 4 { + return ints[0], ints[1], ints[2], ints[3] + } + + return 0, 0, 0, 0 +} + +// parseMargin is an alias for parsePadding since they involve the same logic +// to parse integers to the same format. +var parseMargin = parsePadding diff --git a/style/style.go b/style/style.go new file mode 100644 index 0000000..0b97628 --- /dev/null +++ b/style/style.go @@ -0,0 +1 @@ +package style