summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/builtins.zig56
1 files changed, 34 insertions, 22 deletions
diff --git a/src/builtins.zig b/src/builtins.zig
index dfd1e84c..5818ff51 100644
--- a/src/builtins.zig
+++ b/src/builtins.zig
@@ -244,27 +244,39 @@ test "Exit asks once about unsaved text, and quits when asked again" {
try std.testing.expect(p.quit);
}
-test "Exit over a ctl write names every pane it asks about, and the next Exit discards them all" {
- const p = try Pardes.init(std.testing.allocator, .{ .tty_only = true });
- defer p.deinit();
- const first = try p.setTestFile("saved\n");
- first.file.?.saved_revision = first.file.?.revision -% 1;
- first.file.?.saved_hash = 0; // edited: what it had is not what it has
- p.newScratchBelow(p.active);
- const second = p.panes[p.active].?;
- panes.File.setContent(p, &second.file.?, try std.testing.allocator.dupe(u8, "x" ** 120));
- try std.testing.expect(second.file.?.revision != second.file.?.saved_revision);
- p.fs.no_prompt = true;
- defer p.fs.no_prompt = false;
- try std.testing.expect(p.executeBuiltinLine(p.active, "Exit"));
- try std.testing.expect(!p.quit);
- const said = p.fs.failure[0..p.fs.failure_len];
- try std.testing.expect(std.mem.indexOf(u8, said, first.file.?.path) != null);
- try std.testing.expect(std.mem.indexOf(u8, said, second.file.?.path) != null);
- try std.testing.expect(std.mem.endsWith(u8, said, ": Modified (Exit again to discard)"));
- p.fs.failure_len = 0;
- try std.testing.expect(p.executeBuiltinLine(p.active, "Exit"));
- try std.testing.expect(p.quit);
+test "Exit over a ctl write or a click names every pane it asks about, a second only those edited since, and the next discards them all" {
+ for ([_]bool{ false, true }) |clicked| {
+ const p = try Pardes.init(std.testing.allocator, .{ .tty_only = true });
+ defer p.deinit();
+ const first = try p.setTestFile("saved\n");
+ first.file.?.saved_revision = first.file.?.revision -% 1;
+ first.file.?.saved_hash = 0; // edited: what it had is not what it has
+ p.newScratchBelow(p.active);
+ const second = p.panes[p.active].?;
+ panes.File.setContent(p, &second.file.?, try std.testing.allocator.dupe(u8, "x" ** 120));
+ try std.testing.expect(second.file.?.revision != second.file.?.saved_revision);
+ // A ctl write, or a click through exec (ctl.captured).
+ if (clicked) p.fs.capturing = true else p.fs.no_prompt = true;
+ defer p.fs.capturing = false;
+ defer p.fs.no_prompt = false;
+ try std.testing.expect(p.executeBuiltinLine(p.active, "Exit"));
+ try std.testing.expect(!p.quit);
+ const said = p.fs.failure[0..p.fs.failure_len];
+ try std.testing.expect(std.mem.indexOf(u8, said, first.file.?.path) != null);
+ try std.testing.expect(std.mem.indexOf(u8, said, second.file.?.path) != null);
+ try std.testing.expect(std.mem.endsWith(u8, said, ": Modified (Exit again to discard)"));
+ // Edited since: only that one is named again (acme's rule).
+ p.fs.failure_len = 0;
+ panes.File.setContent(p, &second.file.?, try std.testing.allocator.dupe(u8, "y" ** 120));
+ try std.testing.expect(p.executeBuiltinLine(p.active, "Exit"));
+ try std.testing.expect(!p.quit);
+ const again = p.fs.failure[0..p.fs.failure_len];
+ try std.testing.expect(std.mem.indexOf(u8, again, first.file.?.path) == null);
+ try std.testing.expect(std.mem.startsWith(u8, again, second.file.?.path));
+ p.fs.failure_len = 0;
+ try std.testing.expect(p.executeBuiltinLine(p.active, "Exit"));
+ try std.testing.expect(p.quit);
+ }
}
/// A dump file that exists, for a Restore to get past reading it.
@@ -496,7 +508,7 @@ fn warnModifiedIn(c: Ctx, asking: Pane.Discarding, which: Asked) bool {
all.print("{s}{s}", .{ if (modified) ", " else "", name }) catch {};
modified = true;
}
- if (modified and c.p.fs.no_prompt) {
+ if (modified and (c.p.fs.no_prompt or c.p.fs.capturing)) {
all.print(": Modified ({s} again to discard)", .{@tagName(asking)}) catch {};
const said = @import("Messages.zig").clip(all.buffered(), c.p.fs.failure.len);
@memcpy(c.p.fs.failure[0..said.len], said);