| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657 |
- package common
- import (
- "bytes"
- "image/color"
- "github.com/alecthomas/chroma/v2"
- "github.com/alecthomas/chroma/v2/formatters"
- "github.com/alecthomas/chroma/v2/lexers"
- chromastyles "github.com/alecthomas/chroma/v2/styles"
- "github.com/charmbracelet/crush/internal/ui/styles"
- )
- // SyntaxHighlight applies syntax highlighting to the given source code based
- // on the file name and background color. It returns the highlighted code as a
- // string.
- func SyntaxHighlight(st *styles.Styles, source, fileName string, bg color.Color) (string, error) {
- // Determine the language lexer to use
- l := lexers.Match(fileName)
- if l == nil {
- l = lexers.Analyse(source)
- }
- if l == nil {
- l = lexers.Fallback
- }
- l = chroma.Coalesce(l)
- // Get the formatter
- f := formatters.Get("terminal16m")
- if f == nil {
- f = formatters.Fallback
- }
- style := chroma.MustNewStyle("crush", st.ChromaTheme())
- // Modify the style to use the provided background
- s, err := style.Builder().Transform(
- func(t chroma.StyleEntry) chroma.StyleEntry {
- r, g, b, _ := bg.RGBA()
- t.Background = chroma.NewColour(uint8(r>>8), uint8(g>>8), uint8(b>>8))
- return t
- },
- ).Build()
- if err != nil {
- s = chromastyles.Fallback
- }
- // Tokenize and format
- it, err := l.Tokenise(nil, source)
- if err != nil {
- return "", err
- }
- var buf bytes.Buffer
- err = f.Format(&buf, s, it)
- return buf.String(), err
- }
|