SGR colon sub-parameters — ITU-T T.416 alternative (38:2:: / 48:2:: / 38:5:)
Use `:` (0x3a) instead of `;` (0x3b) between extended-color sub-parameters — the spec-blessed form that disambiguates compound SGR codes from independent ones.
Byte forms
Every common string-literal form so you can paste-and-search either direction.
\x1b[38:2::255:128:64m (T.416) \x1b[38;2;255;128;64m (xterm-legacy)\033[38:2::R:G:Bm\e[38:2::R:G:BmESC [ 38 : 2 :: R : G : B m1b 5b 33 38 3a 32 3a 3a ... 6dDescription
**ITU-T Rec. T.416 / ISO/IEC 8613-6** (1993) — the colon-separator form for SGR sub-parameters. Where xterm's original extended-color introduction used semicolons throughout (`\x1b[38;2;R;G;Bm`), the formal standard reserves `:` (0x3a) as the **sub-parameter separator** within a single SGR parameter, and keeps `;` (0x3b) as the **parameter separator** between independent SGR codes. The shapes are: - **24-bit truecolor**: `\x1b[38:2::R:G:Bm` (fg) / `\x1b[48:2::R:G:Bm` (bg). The empty slot after `2` (yielding the `::`) is the optional **colorspace ID** — empty means RGB, but T.416 allows `38:2:Pcs:R:G:B` where Pcs identifies CIE Lab / CIE u'v'L' / etc. Most emulators ignore Pcs and treat the slot as decorative. - **256-color**: `\x1b[38:5:Nm` / `\x1b[48:5:Nm`. Note: only ONE colon between `5` and `N` here — no empty `::` slot, because the 256-color form has no colorspace argument. - **CMY** (`38:3:Pcs:C:M:Y`) and **CMYK** (`38:4:Pcs:C:M:Y:K`) variants exist in T.416 but are essentially never implemented. **Why this matters**: the original xterm form `\x1b[38;2;R;G;Bm` is **ambiguous** to a strictly-conforming SGR parser. Each semicolon-separated token is supposed to be an independent SGR code, so a strict parser sees `38;2;R;G;B` as five independent codes: `38` (set fg to *next item*), `2` (which it might interpret as 'faint'!), then `R G B` as more SGR codes. The colon form `38:2::R:G:B` is unambiguous because the entire compound is a **single parameter** containing sub-tokens — the colons clearly nest under the `38`. The conformance breakdown: - **Honour the colon form**: kitty (since 0.17), foot, WezTerm, alacritty (since 0.10), ghostty, iTerm2, mlterm, konsole 22.04+, xterm 273+, gnome-terminal recent. - **Honour only the semicolon form**: very old emulators, Windows ConPTY (older), some embedded VT clones. - **Honour both**: every modern emulator in the first list — they parse `;` and `:` as equivalent in the truecolor / 256-color slot to avoid breaking existing software. T.416 also defines colon sub-parameters for **SGR 4 underline styles** — `\x1b[4:0m` (none), `\x1b[4:1m` (single, same as `4m`), `\x1b[4:2m` (double), `\x1b[4:3m` (curly / wavy), `\x1b[4:4m` (dotted), `\x1b[4:5m` (dashed) — and the underline colour pair `\x1b[58:2::R:G:Bm` (set underline colour to RGB) / `\x1b[59m` (default underline colour). The wavy underline is the killer feature here — IDE-style 'misspelled word' visuals at the terminal layer. For portable software, the safe pattern is to **emit the semicolon form** (still understood by every emulator) **but parse both forms** when consuming ANSI bytes from an arbitrary log file.
Spec citation: ITU-T Rec. T.416 (ISO/IEC 8613-6) / xterm-ctlseqs (SGR Pm)
Parameters
| Pcs | Optional colorspace ID after the `2` / `3` / `4` mode byte. Empty (yielding `::`) means RGB / CMY / CMYK in the default colorspace. Most emulators ignore. |
| underline-style | After `4:` — `0` none, `1` single, `2` double, `3` curly, `4` dotted, `5` dashed. Curly (3) is the IDE-style wavy underline. |
Examples
# Strict T.416 truecolor (note the `::`):\nprintf '\033[38:2::255:128:64morange text\033[0m\n'\n# Curly underline for spell-check overlays:\nprintf '\033[4:3mtypo\033[0m\n'import sys\nRGB = (255, 128, 64)\nsys.stdout.write(f'\x1b[38:2::{RGB[0]}:{RGB[1]}:{RGB[2]}morange\x1b[0m\n')\n# Underline colour (T.416 58 / 59):\nsys.stdout.write('\x1b[4m\x1b[58:2::255:0:0merror\x1b[59m\x1b[24m\n')// Emit semicolon form (most portable) but parse both:\nfmt.Print("\x1b[38;2;255;128;64morange\x1b[0m\n")\n// T.416 strict form:\nfmt.Print("\x1b[38:2::255:128:64morange\x1b[0m\n")// Curly underline + RGB underline colour:\nprocess.stdout.write('\x1b[4:3m\x1b[58:2::200:80:80mmisspelled\x1b[59m\x1b[24m\n')/* T.416 256-color: single colon, no empty slot: */\nprintf("\x1b[38:5:208morange-216\x1b[0m\n");\n/* Truecolor with empty colorspace slot: */\nprintf("\x1b[48:2::20:20:60mdeep blue bg\x1b[0m\n");Terminal support
- xterm
- yes
- Linux console (fbcon)
- no
- macOS Terminal.app
- no
- iTerm2
- yes
- Windows Terminal
- partial
- cmd.exe / ConPTY
- no
- kitty
- yes
- alacritty
- yes
- WezTerm
- yes
- Ghostty
- yes
- GNOME Terminal
- yes
- Konsole
- yes
- tmux
- no
- GNU screen
- no
| xterm | Linux console (fbcon) | macOS Terminal.app | iTerm2 | Windows Terminal | cmd.exe / ConPTY | kitty | alacritty | WezTerm | Ghostty | GNOME Terminal | Konsole | tmux | GNU screen |
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| yes | no | no | yes | partial | no | yes | yes | yes | yes | yes | yes | no | no |
Related sequences
In the family cookbook
SGR cookbook · 6. SGR colon sub-params — the standards-correct form