a73x

9e189dbc

Clarify row rebuild cache contract

a73x   2026-04-08 19:16

Commit message
Clarify row rebuild cache contract

src/main.zig
Old New
@@ -750,7 +750,7 @@ test "rebuildRowInstances emits expected instances for a colored glyph row" {
750 atlas.cursorUV(), 750 atlas.cursorUV(),
751 ); 751 );
752 752
753 try std.testing.expect(rebuilt); 753 try std.testing.expect(rebuilt.len_changed);
754 try std.testing.expectEqual(@as(usize, 2), cache.instances.items.len); 754 try std.testing.expectEqual(@as(usize, 2), cache.instances.items.len);
755 755
756 const colors = term.cellColors(row_cells.get(0)); 756 const colors = term.cellColors(row_cells.get(0));
@@ -784,6 +784,8 @@ test "rebuildRowInstances replaces stale cached contents without layout dirtines
784 784
785 var cache = RowInstanceCache{}; 785 var cache = RowInstanceCache{};
786 defer cache.instances.deinit(std.testing.allocator); 786 defer cache.instances.deinit(std.testing.allocator);
787 cache.gpu_offset_instances = 17;
788 cache.gpu_len_instances = 29;
787 try cache.instances.append(std.testing.allocator, .{ 789 try cache.instances.append(std.testing.allocator, .{
788 .cell_pos = .{ 99.0, 99.0 }, 790 .cell_pos = .{ 99.0, 99.0 },
789 .glyph_size = .{ 1.0, 1.0 }, 791 .glyph_size = .{ 1.0, 1.0 },
@@ -817,10 +819,17 @@ test "rebuildRowInstances replaces stale cached contents without layout dirtines
817 atlas.cursorUV(), 819 atlas.cursorUV(),
818 ); 820 );
819 821
820 try std.testing.expect(!rebuilt); 822 try std.testing.expect(!rebuilt.len_changed);
821 try std.testing.expectEqual(@as(usize, 2), cache.instances.items.len); 823 try std.testing.expectEqual(@as(usize, 2), cache.instances.items.len);
822 try std.testing.expectEqualDeep([2]f32{ 0.0, 0.0 }, cache.instances.items[0].cell_pos); 824 try std.testing.expectEqualDeep([2]f32{ 0.0, 0.0 }, cache.instances.items[0].cell_pos);
823 try std.testing.expectEqualDeep([2]f32{ 0.0, 0.0 }, cache.instances.items[1].cell_pos); 825 try std.testing.expectEqualDeep([2]f32{ 0.0, 0.0 }, cache.instances.items[1].cell_pos);
826 try std.testing.expectEqualDeep([2]f32{ @floatFromInt(face.cellWidth()), @floatFromInt(face.cellHeight()) }, cache.instances.items[0].glyph_size);
827 try std.testing.expectEqualDeep(term.cellColors(row_cells.get(0)).bg, cache.instances.items[0].fg);
828 try std.testing.expectEqualDeep(term.cellColors(row_cells.get(0)).bg, cache.instances.items[0].bg);
829 try std.testing.expectEqualDeep(term.cellColors(row_cells.get(0)).fg, cache.instances.items[1].fg);
830 try std.testing.expectEqualDeep(term.cellColors(row_cells.get(0)).bg, cache.instances.items[1].bg);
831 try std.testing.expectEqual(@as(u32, 0), cache.gpu_offset_instances);
832 try std.testing.expectEqual(@as(u32, 0), cache.gpu_len_instances);
824 } 833 }
825 834
826 test "RenderCache resizeRows preserves surviving row caches" { 835 test "RenderCache resizeRows preserves surviving row caches" {
@@ -1011,6 +1020,10 @@ const RowPackResult = struct {
1011 cursor_len_instances: u32, 1020 cursor_len_instances: u32,
1012 }; 1021 };
1013 1022
1023 const RowRebuildResult = struct {
1024 len_changed: bool,
1025 };
1026
1014 fn repackRowCaches( 1027 fn repackRowCaches(
1015 alloc: std.mem.Allocator, 1028 alloc: std.mem.Allocator,
1016 packed_instances: *std.ArrayListUnmanaged(renderer.Instance), 1029 packed_instances: *std.ArrayListUnmanaged(renderer.Instance),
@@ -1056,9 +1069,11 @@ fn rebuildRowInstances(
1056 baseline: u32, 1069 baseline: u32,
1057 default_bg: [4]f32, 1070 default_bg: [4]f32,
1058 bg_uv: font.GlyphUV, 1071 bg_uv: font.GlyphUV,
1059 ) !bool { 1072 ) !RowRebuildResult {
1060 const old_len = cache.instances.items.len; 1073 const old_len = cache.instances.items.len;
1061 cache.instances.clearRetainingCapacity(); 1074 cache.instances.clearRetainingCapacity();
1075 cache.gpu_offset_instances = 0;
1076 cache.gpu_len_instances = 0;
1062 1077
1063 const raw_cells = row_cells.items(.raw); 1078 const raw_cells = row_cells.items(.raw);
1064 var col_idx: u32 = 0; 1079 var col_idx: u32 = 0;
@@ -1085,7 +1100,9 @@ fn rebuildRowInstances(
1085 ); 1100 );
1086 } 1101 }
1087 1102
1088 return markLayoutDirtyOnLenChange(old_len, cache.instances.items.len); 1103 return .{
1104 .len_changed = markLayoutDirtyOnLenChange(old_len, cache.instances.items.len),
1105 };
1089 } 1106 }
1090 1107
1091 fn markLayoutDirtyOnLenChange(old_len: usize, new_len: usize) bool { 1108 fn markLayoutDirtyOnLenChange(old_len: usize, new_len: usize) bool {