diff options
Diffstat (limited to 'src/Output.zig')
| -rw-r--r-- | src/Output.zig | 43 |
1 files changed, 34 insertions, 9 deletions
diff --git a/src/Output.zig b/src/Output.zig index 3b8e6a7a..1461757f 100644 --- a/src/Output.zig +++ b/src/Output.zig @@ -418,6 +418,16 @@ pub fn open(p: *Pardes, id: usize, dir: []const u8, from: Origin, arg: []const u /// Find and Grep share one +Search a directory, each run replacing what /// the last showed, as acme reuses a directory's +Errors; a pane's own /// search (LookWord list) keeps a pane a pattern. +/// Whether `dir` has its Find/Grep +Search open. +pub fn hasFileSearch(p: *Pardes, dir: []const u8) bool { + for (p.panes) |slot| { + const f = (slot orelse continue).file orelse continue; + const o = f.output orelse continue; + if (fileSearch(o.from) and std.mem.eql(u8, std.fs.path.dirname(f.path) orelse "", dir)) return true; + } + return false; +} + fn fileSearch(from: Origin) bool { return switch (from) { .cmd => |c| c == .Find or c == .Grep, @@ -436,7 +446,9 @@ pub fn fillResults(p: *Pardes, id: usize, dir: []const u8, from: Origin, arg: [] const by_arg = std.meta.activeTag(from) != .query; if (p.locations_config.context == 0 and !p.locations_config.tscontext) { for (p.panes, 0..) |slot, i| { - if (i == id) continue; + // A directory's +Search is found by its directory, whatever + // pane ran the search: that +Search itself too. + if (i == id and !fileSearch(from)) continue; const rp = slot orelse continue; const rf = if (rp.file) |*f| f else continue; const output = if (rf.output) |*o| o else continue; @@ -446,6 +458,7 @@ pub fn fillResults(p: *Pardes, id: usize, dir: []const u8, from: Origin, arg: [] if (!locations.sameInput(content, rf.content, rf.location_rows, p.locations_config.layout)) continue; try setArg(output, arg); p.gpa.free(content); + p.fs.refilled = rp.serial; p.active = id; if (traits(from).steps) { pane.search_pane = i; @@ -463,11 +476,11 @@ pub fn fillResults(p: *Pardes, id: usize, dir: []const u8, from: Origin, arg: [] anchor = formatted.anchor; } for (p.panes, 0..) |slot, i| { - if (i == id) continue; const rp = slot orelse continue; const rf = if (rp.file) |*f| f else continue; const o = if (rf.output) |*x| x else continue; const shared = fileSearch(from) and fileSearch(o.from); + if (i == id and !shared) continue; if (!shared and !std.meta.eql(o.from, from)) continue; if (!shared and by_arg and !std.mem.eql(u8, o.arg(), arg)) continue; if (!std.mem.eql(u8, std.fs.path.dirname(rf.path) orelse "", dir)) continue; @@ -555,13 +568,22 @@ pub fn recentText(p: *Pardes, w: *std.Io.Writer, look_rows: bool) !void { for (p.panes) |slot| if (slot) |pane| if (pane.file) |f| if (f.output == null and std.mem.eql(u8, f.path, e.path)) { is_open = true; }; - const state: []const u8 = if (is_open) "open" else "closed"; - if (!look_rows) - try w.print("{s} {s}\n", .{ state, e.path }) - else if (e.line == 0) - try w.print("{s} {s}\n", .{ e.path, state }) - else + const state: []const u8 = if (is_open) "open" else "(closed)"; + if (!look_rows) { + // A name as /index shows it: one line, a newline in it `\n`. + var name_buf: [4 * 4096]u8 = undefined; + try w.print("{s} {s}\n", .{ if (is_open) "open" else "closed", pardes.ctlfs.events.shown(e.path, &name_buf) }); + } else if (e.line == 0) { + try w.print("{s} {s}\n", .{ e.path, state }); + } else if (e.aline != 0 and (e.aline != e.line or e.acol != e.col)) { + // A selection: both its ends, in order, `path:L:C-L2:C2`. + const a_first = e.aline < e.line or (e.aline == e.line and e.acol < e.col); + const s = if (a_first) [2]u32{ e.aline, e.acol } else [2]u32{ e.line, e.col }; + const t = if (a_first) [2]u32{ e.line, e.col } else [2]u32{ e.aline, e.acol }; + try w.print("{s}:{d}:{d}-{d}:{d} {s}\n", .{ e.path, s[0], s[1], t[0], t[1], state }); + } else { try w.print("{s}:{d}:{d} {s}\n", .{ e.path, e.line, e.col, state }); + } } } @@ -647,7 +669,10 @@ pub fn openFonts(p: *Pardes, id: usize) !void { fn openStepped(p: *Pardes, id: usize, from: Origin, content: []u8) !void { errdefer p.gpa.free(content); const pane = p.panes[id] orelse return error.MissingPane; - const dir = if (pane.file) |f| (std.fs.path.dirname(f.path) orelse "/") else pane.cwdSlice(); + const own = if (pane.file) |f| (std.fs.path.dirname(f.path) orelse "/") else pane.cwdSlice(); + // A terminal whose shell has not said where it is yet (an init file's + // word at boot): the session's directory, not `/`. + const dir = if (own.len == 0) p.sessionDir() else own; const free = p.freeSlot() orelse return error.NoPaneSlots; _ = try open(p, free, dir, from, "", content); exec.placeNew(p, id, id, free, .doc); |
