summaryrefslogtreecommitdiff
path: root/src/body_layer.zig
diff options
context:
space:
mode:
Diffstat (limited to 'src/body_layer.zig')
-rw-r--r--src/body_layer.zig23
1 files changed, 23 insertions, 0 deletions
diff --git a/src/body_layer.zig b/src/body_layer.zig
index c8e229c4..a354512f 100644
--- a/src/body_layer.zig
+++ b/src/body_layer.zig
@@ -477,6 +477,29 @@ pub fn renderBody(p: *Pardes, arena: std.mem.Allocator, pane: *Pane, r: Rect, id
}
}
+ // `gw`'s labels, two letters over the start of each word
+ if (pane.jump.items.len > 0) labels: {
+ const flat = edit.flatSurface(p, &pane.body) catch break :labels;
+ const letters = config.jump_label_alphabet;
+ const style: CellStyle = .{ .fg = .{ .rgb = th.sel_fg }, .bg = .{ .rgb = th.sel_bg }, .bold = true };
+ for (pane.jump.items, 0..) |word, i| {
+ if (pane.jump_first) |first| if (i / letters.len != first) continue;
+ var at = @min(word.anchor, word.head);
+ for ([_]u8{ letters[i / letters.len], letters[i % letters.len] }) |letter| {
+ const pos = modal.positionAt(flat, at);
+ const row: i32 = @intCast(pos.row);
+ const wp = pane.wrapRow(row, @intCast(pos.col));
+ const cx = if (pane.file != null)
+ @as(i32, panes.File.gutterWidth(pane)) + panes.File.displayOffset(pane, row, wp.at, @intCast(pos.col))
+ else
+ panes.File.lineDisplayOffset(modal.lineSlice(flat, pos.row), @intCast(@max(0, wp.at)), pos.col);
+ if (wp.row >= 0 and wp.row < body_h and cx >= 0 and cx < tw)
+ s.set(tx + @as(u16, @intCast(cx)), body_y + @as(u16, @intCast(wp.row)), &.{letter}, style);
+ at = modal.nextGrapheme(flat, at);
+ }
+ }
+ }
+
// cursor: tracks the shell cursor until pinned by a click or a key
// (the tag's or a prompt's cursor wins while that is being typed into)
if (active and pane.focus == .body and (pane.prompt == .none or pane.prompt == .del_side or pane.prompt == .repl_choice)) {