fix: handle all pyte color formats for Rich compatibility

- Add 'brown' -> 'yellow' mapping (pyte uses 'brown' for ANSI yellow)
- Add helper function to convert hex colors (pyte outputs 'ff8700',
  Rich needs '#ff8700')
- Handles 256-color and truecolor (24-bit) ANSI codes properly

Bumps version to 0.1.14.
This commit is contained in:
GitHub Copilot
2026-01-24 11:21:09 +00:00
parent 4566d03aa5
commit 0d53952ff7
2 changed files with 19 additions and 4 deletions
+1 -1
View File
@@ -1,6 +1,6 @@
[tool.poetry] [tool.poetry]
name = "textual-webterm" name = "textual-webterm"
version = "0.1.13" version = "0.1.14"
description = "Serve terminal sessions over the web" description = "Serve terminal sessions over the web"
authors = ["Will McGugan <will@textualize.io>"] authors = ["Will McGugan <will@textualize.io>"]
license = "MIT" license = "MIT"
+18 -3
View File
@@ -53,8 +53,23 @@ PYTE_TO_RICH_COLOR = {
"brightmagenta": "bright_magenta", "brightmagenta": "bright_magenta",
"brightcyan": "bright_cyan", "brightcyan": "bright_cyan",
"brightwhite": "bright_white", "brightwhite": "bright_white",
"brown": "yellow", # pyte uses 'brown' for ANSI yellow
} }
def _pyte_color_to_rich(color: str) -> str:
"""Convert pyte color to Rich-compatible color string."""
if color == "default":
return color
# Check mapping first
if color in PYTE_TO_RICH_COLOR:
return PYTE_TO_RICH_COLOR[color]
# If it looks like a hex color without #, add it
if len(color) == 6 and all(c in "0123456789abcdefABCDEF" for c in color):
return f"#{color}"
return color
WEBTERM_STATIC_PATH = Path(__file__).parent / "static" WEBTERM_STATIC_PATH = Path(__file__).parent / "static"
@@ -546,12 +561,12 @@ class LocalServer:
char_data = char["data"] char_data = char["data"]
# Build Rich style from pyte character attributes # Build Rich style from pyte character attributes
# Map pyte color names to Rich-compatible names # Convert pyte color names to Rich-compatible format
style_kwargs = {} style_kwargs = {}
if char["fg"] != "default": if char["fg"] != "default":
style_kwargs["color"] = PYTE_TO_RICH_COLOR.get(char["fg"], char["fg"]) style_kwargs["color"] = _pyte_color_to_rich(char["fg"])
if char["bg"] != "default": if char["bg"] != "default":
style_kwargs["bgcolor"] = PYTE_TO_RICH_COLOR.get(char["bg"], char["bg"]) style_kwargs["bgcolor"] = _pyte_color_to_rich(char["bg"])
if char["bold"]: if char["bold"]:
style_kwargs["bold"] = True style_kwargs["bold"] = True
if char["italics"]: if char["italics"]: