Skip to content

Commit

Permalink
Merge pull request #654 from noborus/fix-escape-sequence
Browse files Browse the repository at this point in the history
Change to use tcell.PaletteColor
  • Loading branch information
noborus authored Nov 13, 2024
2 parents fee39fe + 387f0f8 commit a0ca6de
Show file tree
Hide file tree
Showing 3 changed files with 64 additions and 81 deletions.
9 changes: 0 additions & 9 deletions oviewer/content_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -247,15 +247,6 @@ func Test_StrToContentsStyle1(t *testing.T) {
{width: 1, style: tcell.StyleDefault.Background(tcell.ColorGray), mainc: rune('c'), combc: nil},
},
},
{
name: "216 color",
args: args{
line: "\x1B[38;5;31mc\x1B[m", tabWidth: 8,
},
want: contents{
{width: 1, style: tcell.StyleDefault.Foreground(tcell.NewRGBColor(0, 102, 153)), mainc: 'c', combc: nil},
},
},
{
name: "256",
args: args{
Expand Down
114 changes: 44 additions & 70 deletions oviewer/convert_es.go
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,7 @@ func csToStyle(style tcell.Style, params string) tcell.Style {
if params == "0" || params == "" || params == ";" {
return tcell.StyleDefault.Normal()
}

if s, ok := csiCache.Load(params); ok {
style = applyStyle(style, s.(OVStyle))
return style
Expand All @@ -180,8 +181,7 @@ func csToStyle(style tcell.Style, params string) tcell.Style {
func parseCSI(params string) OVStyle {
s := OVStyle{}
fields := strings.Split(params, ";")
fl := len(fields)
for index := 0; index < fl; index++ {
for index := 0; index < len(fields); index++ {
field := fields[index]
switch field {
case "1", "01":
Expand Down Expand Up @@ -218,12 +218,20 @@ func parseCSI(params string) OVStyle {
s.UnStrikeThrough = true
case "30", "31", "32", "33", "34", "35", "36", "37":
colorNumber, _ := strconv.Atoi(field)
s.Foreground = colorName(int(tcell.Color(colorNumber - 30)))
s.Foreground = colorName(colorNumber - 30)
case "38":
i, color := csColor(fields[index:])
index += i
s.Foreground = color
case "39":
s.Foreground = "default"
case "40", "41", "42", "43", "44", "45", "46", "47":
colorNumber, _ := strconv.Atoi(field)
s.Background = colorName(int(tcell.Color(colorNumber - 40)))
s.Background = colorName(colorNumber - 40)
case "48":
i, color := csColor(fields[index:])
index += i
s.Background = color
case "49":
s.Background = "default"
case "53":
Expand All @@ -232,89 +240,55 @@ func parseCSI(params string) OVStyle {
s.UnOverLine = true
case "90", "91", "92", "93", "94", "95", "96", "97":
colorNumber, _ := strconv.Atoi(field)
s.Foreground = colorName(int(tcell.Color(colorNumber - 82)))
s.Foreground = colorName(colorNumber - 82)
case "100", "101", "102", "103", "104", "105", "106", "107":
colorNumber, _ := strconv.Atoi(field)
s.Background = colorName(int(tcell.Color(colorNumber - 92)))
case "38", "48":
var i int
i, s = csColor(s, fields[index:])
index += i
s.Background = colorName(colorNumber - 92)
}
}
return s
}

// csColor parses 8-bit color and 24-bit color.
func csColor(s OVStyle, fields []string) (int, OVStyle) {
func csColor(fields []string) (int, string) {
if len(fields) < 2 {
return 1, s
return 1, ""
}

var color string
index := 0
fg := fields[index]
index++
if fields[index] == "5" && len(fields) > index+1 { // 8-bit colors.
index++
c, _ := strconv.Atoi(fields[index])
color = colorName(c)
} else if fields[index] == "2" && len(fields) > index+3 { // 24-bit colors.
red, _ := strconv.Atoi(fields[index+1])
green, _ := strconv.Atoi(fields[index+2])
blue, _ := strconv.Atoi(fields[index+3])
index := 1
color := "default"
switch fields[1] {
case "5": // 8-bit colors.
if len(fields) > index+1 {
eColor := fields[2]
if eColor == "" {
return index, color
}
c, err := strconv.Atoi(eColor)
if err != nil {
return index, color
}
index++
color = colorName(c)
}
case "2": // 24-bit colors.
if len(fields) <= index+3 {
index += len(fields) // Skip the Invalid fields.
return index, color
}
red, _ := strconv.Atoi(fields[2])
green, _ := strconv.Atoi(fields[3])
blue, _ := strconv.Atoi(fields[4])
index += 3
color = fmt.Sprintf("#%02x%02x%02x", red, green, blue)
}
if len(color) > 0 {
if fg == "38" {
s.Foreground = color
} else {
s.Background = color
}
}
return index, s
return index, color
}

// colorName returns a string that can be used to specify the color of tcell.
func colorName(colorNumber int) string {
if colorNumber <= 7 {
return lookupColor(colorNumber)
} else if colorNumber <= 15 {
return lookupColor(colorNumber)
} else if colorNumber <= 231 {
red := (colorNumber - 16) / 36
green := ((colorNumber - 16) / 6) % 6
blue := (colorNumber - 16) % 6
return fmt.Sprintf("#%02x%02x%02x", 255*red/5, 255*green/5, 255*blue/5)
} else if colorNumber <= 255 {
grey := 255 * (colorNumber - 232) / 23
return fmt.Sprintf("#%02x%02x%02x", grey, grey, grey)
}
return ""
}

// lookupColor returns the color name from the color number.
func lookupColor(colorNumber int) string {
if colorNumber < 0 || colorNumber > 15 {
return "black"
if colorNumber < 0 || colorNumber > 255 {
return ""
}
return [...]string{
"black",
"maroon",
"green",
"olive",
"navy",
"purple",
"teal",
"silver",
"gray",
"red",
"lime",
"yellow",
"blue",
"fuchsia",
"aqua",
"white",
}[colorNumber]
return tcell.PaletteColor(colorNumber).String()
}
22 changes: 20 additions & 2 deletions oviewer/convert_es_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -282,6 +282,24 @@ func Test_parseCSI(t *testing.T) {
StrikeThrough: false,
},
},
{
name: "test-forground2",
args: args{
params: "38;5;2",
},
want: OVStyle{
Foreground: "green",
},
},
{
name: "test-forground216",
args: args{
params: "38;5;216",
},
want: OVStyle{
Foreground: "#FFAF87",
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
Expand Down Expand Up @@ -313,7 +331,7 @@ func Test_colorName(t *testing.T) {
args: args{
colorNumber: 249,
},
want: "#bcbcbc",
want: "#B2B2B2",
},
{
name: "test-ColorNameNotImplemented",
Expand All @@ -327,7 +345,7 @@ func Test_colorName(t *testing.T) {
args: args{
colorNumber: -1,
},
want: "black",
want: "",
},
}
for _, tt := range tests {
Expand Down

0 comments on commit a0ca6de

Please sign in to comment.