class Tput::Emulator

Overview

Class for terminal emulator program detection.

Best-effort only: detection relies on environment variables, which are inherited by child processes. E.g. opening an xterm inside an lxterminal propagates xterm-specific env vars into lxterm, confusing the detection.

Included Modules

Defined in:

tput/dump.cr
tput/emulator.cr

Constant Summary

Log = ::Log.for((self.name.gsub("::", '.')).underscore)
OCTANT_SUPPORT = Hash(String, String | ::Nil) {"iTerm2" => nil, "Apple Terminal" => nil, "kitty" => "0.40.0", "Ghostty" => "1.1.0", "WezTerm" => nil, "foot" => "1.19.0"}

Per-terminal octant (U+1CD00) support; same format as SEXTANT_SUPPORT. Octants are Unicode 16.0 (2024), so even self-rendering terminals only gained them recently — encode those as identity => "min.version".

SEXTANT_SUPPORT = Hash(String, String | ::Nil) {"iTerm2" => nil, "Apple Terminal" => nil}

Per-terminal sextant (U+1FB00) support. Key is #identity; value is the minimum #version that supports it, or nil for "not supported at any version". Terminals absent from the table are trusted (optimistic default).

Constructors

Class Method Summary

Instance Method Summary

Constructor Detail

def self.new(pull : JSON::PullParser) #

[View source]
def self.new(tput : Tput) #

Creates an instance of Features and performs the autodetection.


[View source]

Class Method Detail

def self.modern_font_env?(env = ENV) : Bool #

Whether env alone identifies one of the #modern_font? terminals (kitty, WezTerm, Ghostty, iTerm2). The static counterpart for consumers that must answer from an env snapshot with no live tty/Tput — e.g. a headless layout pass choosing a glyph tier. The instance predicate is sharper: it also folds in the terminal name and XTVERSION probe refinement, so prefer it whenever a Tput exists.


[View source]

Instance Method Detail

def best_graphics : GraphicsProtocol #

The most capable in-band graphics protocol this terminal advertises. GraphicsProtocol::None means "no pixel graphics; use cell/glyph rendering".


[View source]
def detections : Hash(String, Tput::Detection) #

{name => Detection} for every emulator flag, with provenance.


[View source]
def foot=(foot : Bool) #

Is the emulator foot? (graphics-capable)


[View source]
def foot? : Bool #

Is the emulator foot? (graphics-capable)


[View source]
def ghostty=(ghostty : Bool) #

Is the emulator Ghostty? (graphics-capable)


[View source]
def ghostty? : Bool #

Is the emulator Ghostty? (graphics-capable)


[View source]
def graphics_detections : Hash(String, Tput::Detection) #

{name => Detection} for the derived graphics capabilities — computed from the emulator flags above rather than detected directly, so they have no #sources entry and carry a synthesized provenance instead.


[View source]
def identity : String | Nil #

Best-guess canonical product name, or nil if nothing matched. Concrete products are preferred over generic families (vte/xterm); multiplexers are reported separately via #multiplexer.


[View source]
def inspect(io) #

[View source]
def iterm2=(iterm2 : Bool) #

Is the emulator iTerm2?


[View source]
def iterm2? : Bool #

Is the emulator iTerm2?


[View source]
def iterm_images? : Bool #

Whether the terminal renders iTerm2 inline images (OSC 1337).


[View source]
def kitty=(kitty : Bool) #

Is the emulator kitty? (graphics-capable)


[View source]
def kitty? : Bool #

Is the emulator kitty? (graphics-capable)


[View source]
def kitty_graphics? : Bool #

Whether the terminal speaks the kitty graphics protocol.


[View source]
def konsole=(konsole : Bool) #

Is the emulator KDE Konsole? (graphics-capable)


[View source]
def konsole? : Bool #

Is the emulator KDE Konsole? (graphics-capable)


[View source]
def legacy_computing_octant? : Bool #

Whether the terminal reliably renders legacy-computing octants (U+1CD00…).


[View source]
def legacy_computing_sextant? : Bool #

Whether the terminal reliably renders legacy-computing sextants (U+1FB00…).


[View source]
def lxterm=(lxterm : Bool) #

Is the emulator LXDE's lxterm?


[View source]
def lxterm? : Bool #

Is the emulator LXDE's lxterm?


[View source]
def mlterm=(mlterm : Bool) #

Is the emulator mlterm? (graphics-capable)


[View source]
def mlterm? : Bool #

Is the emulator mlterm? (graphics-capable)


[View source]
def modern_font? : Bool #

Whether the terminal ships with (or is overwhelmingly configured with) a modern, well-covered monospace font — fancy dingbats, geometric shapes beyond the WGL4 set, emoji. Like the legacy-computing ranges above, font coverage has no escape-sequence probe (a missing glyph is same-width tofu), so this is decided from terminal identity: the self-rendering emulators that bundle capable font stacks. Product flags are hardened by #refine_from_probe! (XTVERSION), so a post-probe answer outranks env leakage. Distinct from #legacy_computing_sextant?/octant?: iTerm2's bundled fonts cover dingbats/emoji but not the legacy-computing ranges.


[View source]
def multiplexer : String | Nil #

The terminal multiplexer the program is running inside (tmux/screen), or nil. Separate from #identity since a multiplexer wraps, but doesn't replace, the real terminal underneath.


[View source]
def osxterm=(osxterm : Bool) #

Is the emulator Mac OS X terminal?


[View source]
def osxterm? : Bool #

Is the emulator Mac OS X terminal?


[View source]
def refine_from_probe! : Nil #

Refines identity from the probed XTVERSION string. Called by Tput#probe!.


[View source]
def rxvt=(rxvt : Bool) #

Is the emulator rxvt?


[View source]
def rxvt? : Bool #

Is the emulator rxvt?


[View source]
def screen=(screen : Bool) #

Is the emulator screen?


[View source]
def screen? : Bool #

Is the emulator screen?


[View source]
def self_reported? : Bool #

Whether #identity/#version rest on the terminal's own self-report (XTVERSION, via Tput#probe!) rather than env/TERM heuristics.


[View source]
def sixel? : Bool #

Whether the terminal renders sixel graphics. True for known sixel emulators, or when a DA1 probe reply lists sixel support (device attribute 4). Plain xterm needs -ti vt340 and isn't detectable from env alone, so probe it for certainty.


[View source]
def sources : Hash(String, String) #

For each emulator flag (by name), a description of how it was determined (env var, terminfo/TERM name, etc.). Surfaced via Tput#dump.


[View source]
def term_program : String #

The raw $TERM_PROGRAM value the emulator advertised ("" if unset). Many emulators (Apple Terminal, iTerm2, WezTerm, VS Code, …) self-identify here; paired with #term_program_version.


[View source]
def term_program_version : String #

The raw $TERM_PROGRAM_VERSION value ("" if unset).


[View source]
def terminator=(terminator : Bool) #

Is the emulator terminator?


[View source]
def terminator? : Bool #

Is the emulator terminator?


[View source]
def tmux=(tmux : Bool) #

Is the emulator tmux?


[View source]
def tmux? : Bool #

Is the emulator tmux?


[View source]
def version : String | Nil #

Best-effort version string for the identified terminal, or nil. Prefers the terminal's own XTVERSION self-report (populated by Tput#probe!), falling back to $TERM_PROGRAM_VERSION. XTVERSION usually arrives as name(1.2.3) or name 1.2.3; the bare version is extracted when present.


[View source]
def vte=(vte : Bool) #

Is the emulator based on VTE?


[View source]
def vte? : Bool #

Is the emulator based on VTE?


[View source]
def wezterm=(wezterm : Bool) #

Is the emulator WezTerm? (graphics-capable)


[View source]
def wezterm? : Bool #

Is the emulator WezTerm? (graphics-capable)


[View source]
def xfce=(xfce : Bool) #

Is the emulator XFCE's terminal?


[View source]
def xfce? : Bool #

Is the emulator XFCE's terminal?


[View source]
def xterm=(xterm : Bool) #

Is the emulator xterm?


[View source]
def xterm? : Bool #

Is the emulator xterm?


[View source]