refactor: update completions only if query has changed
This commit is contained in:
parent
a21db7b220
commit
96137de780
2 changed files with 39 additions and 21 deletions
|
|
@ -31,10 +31,10 @@ pub const Entry = struct {
|
||||||
|
|
||||||
pub const ValueType = struct {
|
pub const ValueType = struct {
|
||||||
editor: *ed.Editor = undefined,
|
editor: *ed.Editor = undefined,
|
||||||
start: ed.CurSel = .{},
|
|
||||||
cursor: ed.Cursor = .{},
|
cursor: ed.Cursor = .{},
|
||||||
view: ed.View = .{},
|
view: ed.View = .{},
|
||||||
replace: ?Buffer.Selection = null,
|
query: ?Buffer.Selection = null,
|
||||||
|
last_query: ?[]const u8 = null,
|
||||||
commands: command.Collection(cmds) = undefined,
|
commands: command.Collection(cmds) = undefined,
|
||||||
};
|
};
|
||||||
pub const defaultValue: ValueType = .{};
|
pub const defaultValue: ValueType = .{};
|
||||||
|
|
@ -55,8 +55,7 @@ pub fn load_entries(self: *Type) !usize {
|
||||||
var existing: std.StringHashMapUnmanaged(void) = .empty;
|
var existing: std.StringHashMapUnmanaged(void) = .empty;
|
||||||
defer existing.deinit(self.allocator);
|
defer existing.deinit(self.allocator);
|
||||||
|
|
||||||
self.value.start = self.value.editor.get_primary().*;
|
self.value.query = null;
|
||||||
self.value.replace = null;
|
|
||||||
var iter: []const u8 = self.value.editor.completions.data.items;
|
var iter: []const u8 = self.value.editor.completions.data.items;
|
||||||
while (iter.len > 0) {
|
while (iter.len > 0) {
|
||||||
var cbor_item: []const u8 = undefined;
|
var cbor_item: []const u8 = undefined;
|
||||||
|
|
@ -67,8 +66,8 @@ pub fn load_entries(self: *Type) !usize {
|
||||||
if (existing.contains(dup_text)) continue;
|
if (existing.contains(dup_text)) continue;
|
||||||
try existing.put(self.allocator, dup_text, {});
|
try existing.put(self.allocator, dup_text, {});
|
||||||
|
|
||||||
if (self.value.replace == null) if (get_replace_selection(self.value.editor, values)) |replace| {
|
if (self.value.query == null) if (get_query_selection(self.value.editor, values)) |query| {
|
||||||
self.value.replace = replace;
|
self.value.query = query;
|
||||||
};
|
};
|
||||||
const item = try self.entries.addOne(self.allocator);
|
const item = try self.entries.addOne(self.allocator);
|
||||||
item.* = .{
|
item.* = .{
|
||||||
|
|
@ -98,6 +97,7 @@ pub fn load_entries(self: *Type) !usize {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn deinit(self: *Type) void {
|
pub fn deinit(self: *Type) void {
|
||||||
|
if (self.value.last_query) |p| self.allocator.free(p);
|
||||||
self.value.commands.deinit();
|
self.value.commands.deinit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -115,20 +115,39 @@ pub fn handle_event(self: *Type, _: tp.pid_ref, m: tp.message) tp.result {
|
||||||
{
|
{
|
||||||
tp.self_pid().send(.{ "cmd", "palette_menu_cancel" }) catch |e| self.logger.err(module_name, e);
|
tp.self_pid().send(.{ "cmd", "palette_menu_cancel" }) catch |e| self.logger.err(module_name, e);
|
||||||
} else {
|
} else {
|
||||||
update_query(self, cursor) catch |e| self.logger.err(module_name, e);
|
const query = get_query_text_nostore(self, cursor, self.allocator) catch |e| switch (e) {
|
||||||
|
error.Stop => return,
|
||||||
|
else => |e_| {
|
||||||
|
self.logger.err(module_name, e_);
|
||||||
|
return;
|
||||||
|
},
|
||||||
|
};
|
||||||
|
defer self.allocator.free(query);
|
||||||
|
if (self.value.last_query) |last| {
|
||||||
|
if (!std.mem.eql(u8, query, last))
|
||||||
|
update_query(self, cursor) catch |e| self.logger.err(module_name, e);
|
||||||
|
} else update_query(self, cursor) catch |e| self.logger.err(module_name, e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn initial_query(self: *Type, allocator: std.mem.Allocator) error{ Stop, OutOfMemory }![]const u8 {
|
pub fn initial_query(self: *Type, allocator: std.mem.Allocator) error{ Stop, OutOfMemory }![]const u8 {
|
||||||
return get_query_text(self, self.value.cursor, allocator);
|
return allocator.dupe(u8, try get_query_text(self, self.value.cursor, allocator));
|
||||||
|
}
|
||||||
|
|
||||||
|
fn get_query_text_nostore(self: *Type, cursor: ed.Cursor, allocator: std.mem.Allocator) error{ Stop, OutOfMemory }![]const u8 {
|
||||||
|
return if (self.value.query) |query| blk: {
|
||||||
|
const sel: Buffer.Selection = .{ .begin = query.begin, .end = cursor };
|
||||||
|
break :blk try self.value.editor.get_selection(sel, allocator);
|
||||||
|
} else allocator.dupe(u8, "");
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_query_text(self: *Type, cursor: ed.Cursor, allocator: std.mem.Allocator) error{ Stop, OutOfMemory }![]const u8 {
|
fn get_query_text(self: *Type, cursor: ed.Cursor, allocator: std.mem.Allocator) error{ Stop, OutOfMemory }![]const u8 {
|
||||||
return if (self.value.replace) |replace| blk: {
|
if (self.value.last_query) |p| self.allocator.free(p);
|
||||||
const sel: Buffer.Selection = .{ .begin = replace.begin, .end = cursor };
|
self.value.last_query = null;
|
||||||
break :blk try self.value.editor.get_selection(sel, allocator);
|
const query = try get_query_text_nostore(self, cursor, allocator);
|
||||||
} else allocator.dupe(u8, "");
|
self.value.last_query = query;
|
||||||
|
return query;
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_query(self: *Type, cursor: ed.Cursor) error{OutOfMemory}!void {
|
fn update_query(self: *Type, cursor: ed.Cursor) error{OutOfMemory}!void {
|
||||||
|
|
@ -136,7 +155,6 @@ fn update_query(self: *Type, cursor: ed.Cursor) error{OutOfMemory}!void {
|
||||||
error.Stop => return,
|
error.Stop => return,
|
||||||
else => |e_| return e_,
|
else => |e_| return e_,
|
||||||
};
|
};
|
||||||
defer self.allocator.free(query);
|
|
||||||
self.update_query(query) catch return;
|
self.update_query(query) catch return;
|
||||||
tp.self_pid().send(.{ "cmd", "completion" }) catch |e| self.logger.err(module_name, e);
|
tp.self_pid().send(.{ "cmd", "completion" }) catch |e| self.logger.err(module_name, e);
|
||||||
return;
|
return;
|
||||||
|
|
@ -277,7 +295,7 @@ const TextEdit = struct { newText: []const u8 = &.{}, insert: ?Range = null, rep
|
||||||
const Range = struct { start: Position, end: Position };
|
const Range = struct { start: Position, end: Position };
|
||||||
const Position = struct { line: usize, character: usize };
|
const Position = struct { line: usize, character: usize };
|
||||||
|
|
||||||
pub fn get_replace_selection(editor: *ed.Editor, values: Values) ?Buffer.Selection {
|
pub fn get_query_selection(editor: *ed.Editor, values: Values) ?Buffer.Selection {
|
||||||
return get_replacement_selection(editor, values.insert, values.replace);
|
return get_replacement_selection(editor, values.insert, values.replace);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ const Widget = @import("../../Widget.zig");
|
||||||
|
|
||||||
const Values = @import("completion_dropdown.zig").Values;
|
const Values = @import("completion_dropdown.zig").Values;
|
||||||
const get_values = @import("completion_dropdown.zig").get_values;
|
const get_values = @import("completion_dropdown.zig").get_values;
|
||||||
const get_replace_selection = @import("completion_dropdown.zig").get_replace_selection;
|
const get_query_selection = @import("completion_dropdown.zig").get_query_selection;
|
||||||
|
|
||||||
pub const label = "Select completion";
|
pub const label = "Select completion";
|
||||||
pub const name = "completion";
|
pub const name = "completion";
|
||||||
|
|
@ -32,7 +32,7 @@ pub const Entry = struct {
|
||||||
|
|
||||||
pub const ValueType = struct {
|
pub const ValueType = struct {
|
||||||
start: ed.CurSel = .{},
|
start: ed.CurSel = .{},
|
||||||
replace: ?Buffer.Selection = null,
|
query: ?Buffer.Selection = null,
|
||||||
};
|
};
|
||||||
pub const defaultValue: ValueType = .{};
|
pub const defaultValue: ValueType = .{};
|
||||||
|
|
||||||
|
|
@ -57,8 +57,8 @@ pub fn load_entries(palette: *Type) !usize {
|
||||||
if (existing.contains(dup_text)) continue;
|
if (existing.contains(dup_text)) continue;
|
||||||
try existing.put(palette.allocator, dup_text, {});
|
try existing.put(palette.allocator, dup_text, {});
|
||||||
|
|
||||||
if (palette.value.replace == null) if (get_replace_selection(editor, values)) |replace| {
|
if (palette.value.query == null) if (get_query_selection(editor, values)) |query| {
|
||||||
palette.value.replace = replace;
|
palette.value.query = query;
|
||||||
};
|
};
|
||||||
const item = (try palette.entries.addOne(palette.allocator));
|
const item = (try palette.entries.addOne(palette.allocator));
|
||||||
item.* = .{
|
item.* = .{
|
||||||
|
|
@ -88,9 +88,9 @@ pub fn load_entries(palette: *Type) !usize {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn initial_query(palette: *Type, allocator: std.mem.Allocator) error{OutOfMemory}![]const u8 {
|
pub fn initial_query(palette: *Type, allocator: std.mem.Allocator) error{OutOfMemory}![]const u8 {
|
||||||
return if (palette.value.replace) |replace| blk: {
|
return if (palette.value.query) |query| blk: {
|
||||||
const editor = tui.get_active_editor() orelse break :blk allocator.dupe(u8, "");
|
const editor = tui.get_active_editor() orelse break :blk allocator.dupe(u8, "");
|
||||||
const sel: Buffer.Selection = .{ .begin = replace.begin, .end = palette.value.start.cursor };
|
const sel: Buffer.Selection = .{ .begin = query.begin, .end = palette.value.start.cursor };
|
||||||
break :blk editor.get_selection(sel, allocator) catch break :blk allocator.dupe(u8, "");
|
break :blk editor.get_selection(sel, allocator) catch break :blk allocator.dupe(u8, "");
|
||||||
} else allocator.dupe(u8, "");
|
} else allocator.dupe(u8, "");
|
||||||
}
|
}
|
||||||
|
|
@ -162,7 +162,7 @@ pub fn updated(palette: *Type, button_: ?*Type.ButtonType) !void {
|
||||||
const button = button_ orelse return cancel(palette);
|
const button = button_ orelse return cancel(palette);
|
||||||
const values = get_values(button.opts.label);
|
const values = get_values(button.opts.label);
|
||||||
const editor = tui.get_active_editor() orelse return error.NotFound;
|
const editor = tui.get_active_editor() orelse return error.NotFound;
|
||||||
editor.get_primary().selection = get_replace_selection(editor, values);
|
editor.get_primary().selection = get_query_selection(editor, values);
|
||||||
|
|
||||||
const mv = tui.mainview() orelse return;
|
const mv = tui.mainview() orelse return;
|
||||||
try mv.set_info_content(values.label, .replace);
|
try mv.set_info_content(values.label, .replace);
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue