You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
ANSI printable-suppression window swallows real Tab within 50ms of Shift+Tab #5638
AnsiInputProcessor's 50 ms printable-suppression window (the OnKeyboardEventParsed/ShouldSuppressFallbackKeyDown dedup of dual-reported keys) swallows a real\t keypress arriving within 50 ms of a parsed Shift+Tab (ESC[Z), because GetPrintableText () returns "\t" for both. Fast sequences like Shift+Tab then Tab lose the Tab.
v2.5.0 ecosystem validation (#5630), porting tui-cs/Editor to a preview package built from #5416 head e8aba423 (2.5.0-tig-remove-cm-followup.2).
Repro / evidence
Update to TG 2.5.0-beta.1 Editor#287: test RawAnsi_Tab_After_ShiftTab_Reindents_Line_On_First_Keypress is skipped with this documented; re-enable after the upstream fix.
Impact
Dropped keystrokes under fast input on the ANSI driver (e.g., outdent-then-indent in an editor). Release-gating for v2.5.0 (#5630): fix or waive before Prepare Release.
Found by Claude (Fable 5) agents during the #5630 ecosystem-validation gate.
changed the title [-]v2.5.0 preview: ANSI printable-suppression window swallows real Tab within 50ms of Shift+Tab[/-][+]ANSI printable-suppression window swallows real Tab within 50ms of Shift+Tab[/+]on Aug 23, 2026
I traced this through the history. The repro is valid, but #5602 is not causal: it changed only output-buffer dirty-row handling and did not touch the input pipeline.
The current 50 ms implementation came from #5618 (b2525d126), merged six minutes after #5602. That may be the intended reference.
There is a further nuance: the underlying Shift+Tab → Tab false positive predates #5618. The OnKeyboardEventParsed / ShouldSuppressFallbackKeyDown mechanism was introduced by #4927 (e532d6101). It already behaved as follows:
ESC[Z is parsed as Key.Tab.WithShift.
Shift-modified presses are allowed to arm printable suppression.
GetPrintableText () returns "\t" for Key.Tab.WithShift.
The next raw \t reaches fallback processing, matches the pending text, and is suppressed.
Before #5618, that pending suppression had no expiry. #5618 narrowed it to 50 ms but retained the collision. Its coverage exercises kitty CSI-u plus legacy duplicates, not a complete legacy Shift+Tab report followed by a separate Tab keypress.
The deeper problem is provenance: any parsed keyboard event can arm logic intended to deduplicate kitty plus legacy dual reports. ESC[Z is already a complete Shift+Tab report and should not arm suppression for a following raw Tab. A robust fix should restrict arming to inputs that can legitimately be dual-reported, or preserve parser provenance; matching only text plus elapsed time cannot reliably distinguish two physical keypresses.
Activity
Harden Editor.Text CWP re-entrancy flag; add Text-hiding contract tests
[-]v2.5.0 preview: ANSI printable-suppression window swallows real Tab within 50ms of Shift+Tab[/-][+]ANSI printable-suppression window swallows real Tab within 50ms of Shift+Tab[/+]YourRobotOverlord commentedon Aug 23, 2026
I traced this through the history. The repro is valid, but #5602 is not causal: it changed only output-buffer dirty-row handling and did not touch the input pipeline.
The current 50 ms implementation came from #5618 (
b2525d126), merged six minutes after #5602. That may be the intended reference.There is a further nuance: the underlying Shift+Tab → Tab false positive predates #5618. The
OnKeyboardEventParsed/ShouldSuppressFallbackKeyDownmechanism was introduced by #4927 (e532d6101). It already behaved as follows:ESC[Zis parsed asKey.Tab.WithShift.GetPrintableText ()returns"\t"forKey.Tab.WithShift.\treaches fallback processing, matches the pending text, and is suppressed.Before #5618, that pending suppression had no expiry. #5618 narrowed it to 50 ms but retained the collision. Its coverage exercises kitty CSI-u plus legacy duplicates, not a complete legacy Shift+Tab report followed by a separate Tab keypress.
So the attribution appears to be:
The deeper problem is provenance: any parsed keyboard event can arm logic intended to deduplicate kitty plus legacy dual reports.
ESC[Zis already a complete Shift+Tab report and should not arm suppression for a following raw Tab. A robust fix should restrict arming to inputs that can legitimately be dual-reported, or preserve parser provenance; matching only text plus elapsed time cannot reliably distinguish two physical keypresses.fix(input): scope ANSI key deduplication
fix(input): require adjacent Kitty fallback
Fixes #5638. Scope ANSI key deduplication (#5644)
Update to TG 2.5.0-beta.1 (#287)