docs/tui-alternate-screen.md
This document explains the design decision behind Codex's alternate screen handling, particularly in terminal multiplexers like Zellij. This addresses a fundamental conflict between fullscreen TUI behavior and terminal scrollback history preservation.
Codex's TUI uses the terminal's alternate screen buffer to provide a clean fullscreen experience. This approach:
Terminal multiplexers like Zellij strictly follow the xterm specification, which defines that alternate screen buffers should not have scrollback. This is intentional design, not a bug:
When using Codex's TUI in Zellij, users cannot scroll back through the conversation history because:
Codex implements a pragmatic workaround with three modes, controlled by tui.alternate_screen in config.toml:
auto (default)alwaysneverThe --no-alt-screen CLI flag can override the config setting at runtime:
codex --no-alt-screen
This runs the TUI in inline mode regardless of the configuration, useful for:
The auto mode detects Zellij by checking the ZELLIJ environment variable:
let terminal_info = codex_core::terminal::terminal_info();
!matches!(terminal_info.multiplexer, Some(Multiplexer::Zellij { .. }))
This detection happens in the helper function determine_alt_screen_mode() in codex-rs/tui/src/lib.rs.
The AltScreenMode enum is defined in codex-rs/protocol/src/config_types.rs and serializes to lowercase TOML:
[tui]
# Options: auto, always, never
alternate_screen = "auto"
We use auto detection instead of always disabling in Zellij because:
Codex's transcript pager (opened with Ctrl+T) provides an alternative way to review conversation history, even in fullscreen mode. However, this is not as seamless as natural scrollback.
When modifying TUI code, remember:
determine_alt_screen_mode() function encapsulates all the logicconfig.tui_alternate_screencli.no_alt_screentui.set_alt_screen_enabled()If you encounter issues with terminal state after running Codex, you can restore your terminal with:
reset