Skip to content

Commit 694a3a9

Browse files
committed
Tweak a few things for clarity / future understanding
1 parent 4ca91aa commit 694a3a9

File tree

1 file changed

+20
-18
lines changed

1 file changed

+20
-18
lines changed

codex-rs/tui/src/custom_terminal.rs

Lines changed: 20 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -411,33 +411,35 @@ fn diff_buffers<'a>(a: &'a Buffer, b: &'a Buffer) -> Vec<DrawCommand<'a>> {
411411
let next_buffer = &b.content;
412412

413413
let mut updates = vec![];
414-
let mut last_nonblank_column = vec![0; a.area.height as usize];
414+
let mut last_nonblank_columns = vec![0; a.area.height as usize];
415415
for y in 0..a.area.height {
416416
let row_start = y as usize * a.area.width as usize;
417417
let row_end = row_start + a.area.width as usize;
418418
let row = &next_buffer[row_start..row_end];
419419
let bg = row.last().map(|cell| cell.bg).unwrap_or(Color::Reset);
420420

421-
let mut last_nonblank: Option<usize> = None;
422-
let mut col = 0usize;
423-
while col < row.len() {
424-
let cell = &row[col];
425-
let width = cell.symbol().width().max(1);
421+
// Scan the row to find the rightmost column that still matters: any non-space glyph,
422+
// any cell whose bg differs from the row’s trailing bg, or any cell with modifiers.
423+
// Multi-width glyphs extend that region through their full displayed width.
424+
// After that point the rest of the row can be cleared with a single ClearToEnd, a perf win
425+
// versus emitting multiple space Put commands.
426+
let mut last_nonblank_column = 0usize;
427+
let mut column = 0usize;
428+
while column < row.len() {
429+
let cell = &row[column];
430+
let width = cell.symbol().width();
426431
if cell.symbol() != " " || cell.bg != bg || cell.modifier != Modifier::empty() {
427-
last_nonblank = Some(col + width.saturating_sub(1));
432+
last_nonblank_column = column + (width.saturating_sub(1));
428433
}
429-
col += width;
434+
column += width.max(1); // treat zero-width symbols as width 1
430435
}
431-
let x = last_nonblank.unwrap_or(0);
432-
last_nonblank_column[y as usize] = x as u16;
433-
if x + 1 < row.len() {
434-
let (x_abs, y_abs) = a.pos_of(row_start + x + 1);
435-
updates.push(DrawCommand::ClearToEnd {
436-
x: x_abs,
437-
y: y_abs,
438-
bg,
439-
});
436+
437+
if last_nonblank_column + 1 < row.len() {
438+
let (x, y) = a.pos_of(row_start + last_nonblank_column + 1);
439+
updates.push(DrawCommand::ClearToEnd { x, y, bg });
440440
}
441+
442+
last_nonblank_columns[y as usize] = last_nonblank_column as u16;
441443
}
442444

443445
// Cells invalidated by drawing/replacing preceding multi-width characters:
@@ -449,7 +451,7 @@ fn diff_buffers<'a>(a: &'a Buffer, b: &'a Buffer) -> Vec<DrawCommand<'a>> {
449451
if !current.skip && (current != previous || invalidated > 0) && to_skip == 0 {
450452
let (x, y) = a.pos_of(i);
451453
let row = i / a.area.width as usize;
452-
if x <= last_nonblank_column[row] {
454+
if x <= last_nonblank_columns[row] {
453455
updates.push(DrawCommand::Put {
454456
x,
455457
y,

0 commit comments

Comments
 (0)