diff options
| author | Gabriel Schneider <[email protected]> | 2026-09-28 09:16:36 -0300 |
|---|---|---|
| committer | Gabriel Schneider <[email protected]> | 2026-10-01 00:12:14 -0300 |
| commit | a9de2b51ab76a43250a4d6c41a0ddd54e6970049 (patch) | |
| tree | a2138ead27f434026c224fd8b926f66b7fd7fe0c /src/mouse.zig | |
| parent | 0d04bc9214cccce42d74862b31376d49bdda3956 (diff) | |
| download | pardes-a9de2b51ab76a43250a4d6c41a0ddd54e6970049.tar.gz pardes-a9de2b51ab76a43250a4d6c41a0ddd54e6970049.zip | |
Let the keyboard reach a tag's path, read-only
The tag's computed path, dirty marker and page were out of the keyboard's
reach: its cursor lived in the text after them. It now lives in the tag as
shown, as in acme where the name is ordinary text at the start of the tag, so
`0` goes to the line's start and motions select and yank the path. The path
stays read-only: an edit that would change it is refused and leaves the
cursor where it was, and typing into a file's path drafts a new name as a
click on it does. Sync moves the tag's positions when the prefix changes
length, so a rename or the dirty marker still never moves the cursor off the
text after it.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
Diffstat (limited to 'src/mouse.zig')
| -rw-r--r-- | src/mouse.zig | 21 |
1 files changed, 14 insertions, 7 deletions
diff --git a/src/mouse.zig b/src/mouse.zig index 69feea29..beb2e624 100644 --- a/src/mouse.zig +++ b/src/mouse.zig @@ -827,11 +827,14 @@ fn dragRelease(p: *Pardes, button: Mouse.Button) void { if (sl.r0 < pane.tag_rows) { // On the tag the caret goes where the button came up. A // click on the path, if it can be renamed, drafts a name. - const at = tagline.tagOffsetAt(p, pane, @intCast(@max(0, sl.r1)), @intCast(@max(0, sl.c1))); - if (at) |cursor| { + const row: usize = @intCast(@max(0, sl.r1)); + const col: usize = @intCast(@max(0, sl.c1)); + if (!dragged and tagline.onName(pane, row, col)) { + tagline.draftName(p, pane, col); + } else if (tagline.tagOffsetAt(p, pane, row, col)) |cursor| { pane.tag.cur_row = @intCast(cursor.row); pane.tag.cur_col = @intCast(cursor.col); - } else if (!dragged) tagline.draftName(p, pane, @intCast(@max(0, sl.c1))); + } return; } if (dragged) edit.capturePointerSelection(p, pane, sel_slot) catch {}; @@ -932,7 +935,8 @@ fn chordCutPaste(p: *Pardes, cut: bool) void { }; if (@min(pane.sel[sel_slot].r0, pane.sel[sel_slot].r1) < pane.tag_rows) { // A sweep over the tag cuts from and pastes into the tag's own text; - // the part of it over the prefix is not the tag's to cut. + // the part of it over the prefix is not the tag's to cut, so the + // sweep starts after it. const t = &pane.tag; if (!s.chorded) { s.chorded = true; @@ -941,9 +945,12 @@ fn chordCutPaste(p: *Pardes, cut: bool) void { const forward = sl.r0 < sl.r1 or (sl.r0 == sl.r1 and sl.c0 <= sl.c1); const start = if (forward) .{ sl.r0, sl.c0 } else .{ sl.r1, sl.c1 }; const end = if (forward) .{ sl.r1, sl.c1 } else .{ sl.r0, sl.c0 }; - const origin: modal.Cursor = .{ .row = 0, .col = 0 }; - const from = tagline.tagOffsetAt(p, pane, @intCast(@max(0, start[0])), @intCast(@max(0, start[1]))) orelse origin; - const to = tagline.tagOffsetAt(p, pane, @intCast(@max(0, end[0])), @intCast(@max(0, end[1]))) orelse origin; + const lead = pane.tag_lead; + const origin: modal.Cursor = .{ .row = 0, .col = lead }; + var from = tagline.tagOffsetAt(p, pane, @intCast(@max(0, start[0])), @intCast(@max(0, start[1]))) orelse origin; + var to = tagline.tagOffsetAt(p, pane, @intCast(@max(0, end[0])), @intCast(@max(0, end[1]))) orelse origin; + if (from.row == 0) from.col = @max(from.col, lead); + if (to.row == 0) to.col = @max(to.col, lead); t.cur_row = @intCast(to.row); t.cur_col = @intCast(to.col); t.cur_pinned = true; |
