Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .jules/refract.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,3 +51,7 @@
## 2025-02-19 - C# 13 System.Threading.Lock Modernization
**Observation:** The codebase contained legacy lock statements utilizing an arbitrary object (`object _gate`) for synchronization in `HttpImageResolver.cs`, an obsolete pattern that lacks explicit thread safety semantics compared to modern alternatives.
**Strategic Action:** Transitioned the synchronization mechanism to use the C# 13 `System.Threading.Lock` type (`System.Threading.Lock _gate = new();`) to enforce deterministic thread safety and structural clarity.

## 2025-05-18 - [Escape Sequence Modernization]
**Observation:** Ambiguous `\u001B` and `\x1b` escape sequences used for ANSI escape codes.
**Strategic Action:** Replaced with the C# 13 `\e` escape sequence for precise character representation.
Comment on lines +55 to +57
2 changes: 1 addition & 1 deletion src/Tedd.TUI.Platform.Console/ConsoleInputManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ public ConsoleInputManager(TuiWindow window)
// CSI ? 1000 h (Normal tracking)
// CSI ? 1003 h (All motion tracking)
// CSI ? 1006 h (SGR ext mode)
System.Console.Write("\x1b[?1000h\x1b[?1006h");
System.Console.Write("\e[?1000h\e[?1006h");
}

public IntPtr InputHandle { get; private set; }
Expand Down
2 changes: 1 addition & 1 deletion src/Tedd.TUI.Platform.Console/TuiApp.cs
Original file line number Diff line number Diff line change
Expand Up @@ -181,7 +181,7 @@ public void Stop()
try { _inputManager?.Stop(); } catch { }
try { _platform.Shutdown(); } catch { }

System.Console.Write("\x1b[?1000l\x1b[?1006l");
System.Console.Write("\e[?1000l\e[?1006l");
System.Console.CursorVisible = true;
System.Console.ResetColor();
System.Console.Clear();
Expand Down
2 changes: 1 addition & 1 deletion src/Tedd.TUI.Platform.LinuxTerminal/ITerm2InlineEncoder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ public string Encode(GraphicPlacement placement)
return string.Empty;

var sb = new StringBuilder(placement.ImageData.Length * 4 / 3 + 128);
sb.Append("\x1b]1337;File=inline=1");
sb.Append("\e]1337;File=inline=1");

if (placement.CharWidth > 0)
{
Expand Down
4 changes: 2 additions & 2 deletions src/Tedd.TUI.Platform.LinuxTerminal/KittyGraphicsEncoder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ public string Encode(GraphicPlacement placement)
bool first = offset == 0;
bool last = offset + len >= base64.Length;

sb.Append("\x1b_G");
sb.Append("\e_G");
if (first)
{
sb.Append("a=T,f=100,");
Expand All @@ -43,7 +43,7 @@ public string Encode(GraphicPlacement placement)
sb.Append("m=").Append(last ? '0' : '1');
sb.Append(';');
sb.Append(base64, offset, len);
sb.Append("\x1b\\");
sb.Append("\e\\");
}

return sb.ToString();
Expand Down
4 changes: 2 additions & 2 deletions src/Tedd.TUI.Platform.LinuxTerminal/LinuxTerminalPlatform.cs
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ public void Initialize()
try
{
// Switch to the alt screen, enable SGR mouse mode, hide the cursor.
System.Console.Write("\x1b[?1049h\x1b[?1000h\x1b[?1006h\x1b[?25l");
System.Console.Write("\e[?1049h\e[?1000h\e[?1006h\e[?25l");
_altScreenEntered = true;
}
catch { }
Expand All @@ -111,7 +111,7 @@ public void Shutdown()
{
if (_altScreenEntered)
{
try { System.Console.Write("\x1b[?25h\x1b[?1006l\x1b[?1000l\x1b[?1049l"); } catch { }
try { System.Console.Write("\e[?25h\e[?1006l\e[?1000l\e[?1049l"); } catch { }
_altScreenEntered = false;
}

Expand Down
6 changes: 3 additions & 3 deletions src/Tedd.TUI.Tests/AnsiTrueColorRendererTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,8 @@ public void Render_EmitsTruecolorSgrSequence()
renderer.Render(buffer);

string output = sw.ToString();
Assert.Contains("\x1b[38;2;10;20;30m", output);
Assert.Contains("\x1b[48;2;40;50;60m", output);
Assert.Contains("\e[38;2;10;20;30m", output);
Assert.Contains("\e[48;2;40;50;60m", output);
Comment on lines +23 to +24
Assert.Contains("ABC", output);
}

Expand Down Expand Up @@ -69,7 +69,7 @@ public void Render_InvokesImageEncoderForPlacements()
renderer.Render(buffer);

Assert.Single(recorded);
Assert.Contains("\x1b[1;2H", sw.ToString()); // cursor at row 1, col 2 (1-based)
Assert.Contains("\e[1;2H", sw.ToString()); // cursor at row 1, col 2 (1-based)
Assert.Contains("FAKE", sw.ToString());
}

Expand Down
14 changes: 7 additions & 7 deletions src/Tedd.TUI.Tests/ImageProtocolEncoderTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ public void SixelEncoder_WrapsPayloadInDecPm()
var encoder = new SixelEncoder();
var encoded = encoder.Encode(new GraphicPlacement { CharWidth = 3, CharHeight = 2 });

Assert.StartsWith("\x1bP", encoded);
Assert.EndsWith("\x1b\\", encoded);
Assert.StartsWith("\eP", encoded);
Assert.EndsWith("\e\\", encoded);
Comment on lines +19 to +20
Assert.Contains("q", encoded);
Assert.Equal("sixel", encoder.Protocol);
}
Expand All @@ -43,8 +43,8 @@ public void SixelEncoder_EncodesRgbaPixels()
CharHeight = 1,
});

Assert.StartsWith("\x1bP0;1;0q", encoded);
Assert.EndsWith("\x1b\\", encoded);
Assert.StartsWith("\eP0;1;0q", encoded);
Assert.EndsWith("\e\\", encoded);
Comment on lines +46 to +47
// Each used color must declare itself: "#<idx>;2;<r>;<g>;<b>".
Assert.Matches(@"#\d+;2;100;0;0", encoded); // red
Assert.Matches(@"#\d+;2;0;100;0", encoded); // green
Expand Down Expand Up @@ -78,8 +78,8 @@ public void KittyEncoder_EmitsChunkedBase64()
CharHeight = 2,
});

Assert.StartsWith("\x1b_G", encoded);
Assert.EndsWith("\x1b\\", encoded);
Assert.StartsWith("\e_G", encoded);
Assert.EndsWith("\e\\", encoded);
Comment on lines +81 to +82
Assert.Contains("a=T,f=100", encoded);
Assert.Contains("c=4", encoded);
Assert.Contains("r=2", encoded);
Expand All @@ -106,7 +106,7 @@ public void ITerm2Encoder_EmitsInlineEscape()
MediaType = "image/png",
});

Assert.StartsWith("\x1b]1337;File=inline=1", encoded);
Assert.StartsWith("\e]1337;File=inline=1", encoded);
Assert.EndsWith("\x07", encoded);
Assert.Contains("width=10", encoded);
Assert.Contains("height=5", encoded);
Expand Down
8 changes: 4 additions & 4 deletions src/Tedd.TUI/AnsiTrueColorRenderer.cs
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,7 @@ private void EmitGraphics(VirtualBuffer buffer)
// Park the cursor at the placement's top-left cell so terminals that draw
// images at the current cursor position (Sixel, iTerm2 inline, Kitty default)
// land in the right spot.
sb.Append('\x1b').Append('[').Append(placement.CharY + 1).Append(';').Append(placement.CharX + 1).Append('H');
sb.Append('\e').Append('[').Append(placement.CharY + 1).Append(';').Append(placement.CharX + 1).Append('H');
sb.Append(encoder.Encode(placement));
}

Expand Down Expand Up @@ -199,7 +199,7 @@ private void AppendChar(char c)
private void EmitCursor(int x, int y)
{
// ANSI cursor positioning is 1-based.
_buffer.Append('\x1b').Append('[').Append(y + 1).Append(';').Append(x + 1).Append('H');
_buffer.Append('\e').Append('[').Append(y + 1).Append(';').Append(x + 1).Append('H');
_cursorX = x;
_cursorY = y;
}
Expand All @@ -208,12 +208,12 @@ private void EmitColors(TuiColor fg, TuiColor bg)
{
if (fg.Packed != _currentFg.Packed)
{
_buffer.Append("\x1b[38;2;").Append(fg.R).Append(';').Append(fg.G).Append(';').Append(fg.B).Append('m');
_buffer.Append("\e[38;2;").Append(fg.R).Append(';').Append(fg.G).Append(';').Append(fg.B).Append('m');
_currentFg = fg;
}
if (bg.Packed != _currentBg.Packed)
{
_buffer.Append("\x1b[48;2;").Append(bg.R).Append(';').Append(bg.G).Append(';').Append(bg.B).Append('m');
_buffer.Append("\e[48;2;").Append(bg.R).Append(';').Append(bg.G).Append(';').Append(bg.B).Append('m');
_currentBg = bg;
}
}
Expand Down
8 changes: 4 additions & 4 deletions src/Tedd.TUI/SixelEncoderCore.cs
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ public static string EncodePixels(byte[] pixels, int width, int height)
}

var sb = new StringBuilder(width * height / 6 + 256);
sb.Append("\x1bP0;1;0q"); // P2=1 β†’ background pixels remain transparent.
sb.Append("\eP0;1;0q"); // P2=1 β†’ background pixels remain transparent.

// Raster attributes: pan=1, pad=1 (square pixels), actual w / h.
sb.Append('"').Append(1).Append(';').Append(1).Append(';').Append(width).Append(';').Append(height);
Expand Down Expand Up @@ -149,7 +149,7 @@ public static string EncodePixels(byte[] pixels, int width, int height)
}
}

sb.Append("\x1b\\");
sb.Append("\e\\");
return sb.ToString();
}

Expand Down Expand Up @@ -244,12 +244,12 @@ private static (byte r, byte g, byte b) PaletteRgb(int index)
private static string EncodePlaceholder(int pxW, int pxH)
{
var sb = new StringBuilder(64 + pxW);
sb.Append("\x1bP0;0;0q");
sb.Append("\eP0;0;0q");
sb.Append('"').Append(1).Append(';').Append(1).Append(';').Append(pxW).Append(';').Append(pxH);
sb.Append("#0;2;0;0;0");
sb.Append('#').Append(0);
for (int i = 0; i < pxW; i++) sb.Append('?');
sb.Append("\x1b\\");
sb.Append("\e\\");
return sb.ToString();
}
}
Loading