Fix incorrect highlight

This commit is contained in:
hrsh7th
2021-10-11 00:26:21 +09:00
parent 6790f0a853
commit 67d43ddd59
2 changed files with 35 additions and 27 deletions

View File

@@ -4,10 +4,12 @@ local misc = require('cmp.utils.misc')
local str = require('cmp.utils.str') local str = require('cmp.utils.str')
local config = require('cmp.config') local config = require('cmp.config')
local types = require('cmp.types') local types = require('cmp.types')
local matcher = require('cmp.matcher')
---@class cmp.Entry ---@class cmp.Entry
---@field public id number ---@field public id number
---@field public cache cmp.Cache ---@field public cache cmp.Cache
---@field public match_cache cmp.Cache
---@field public score number ---@field public score number
---@field public exact boolean ---@field public exact boolean
---@field public matches table ---@field public matches table
@@ -32,6 +34,7 @@ entry.new = function(ctx, source, completion_item)
local self = setmetatable({}, { __index = entry }) local self = setmetatable({}, { __index = entry })
self.id = misc.id('entry') self.id = misc.id('entry')
self.cache = cache.new() self.cache = cache.new()
self.match_cache = cache.new()
self.score = 0 self.score = 0
self.exact = false self.exact = false
self.matches = {} self.matches = {}
@@ -337,6 +340,20 @@ entry.get_replace_range = function(self)
end) end)
end end
---Match line.
---@param input string
---@return { score: number, matches: table[] }
entry.match = function(self, input)
return self.match_cache:ensure(input, function()
local score, matches
score, matches = matcher.match(input, self:get_filter_text(), { self:get_word() })
if self:get_filter_text() ~= self:get_completion_item().label then
_, matches = matcher.match(input, self:get_completion_item().label)
end
return { score = score, matches = matches }
end)
end
---Get resolved completion item if possible. ---Get resolved completion item if possible.
---@return lsp.CompletionItem ---@return lsp.CompletionItem
entry.get_completion_item = function(self) entry.get_completion_item = function(self)

View File

@@ -82,7 +82,7 @@ source.get_entries = function(self, ctx)
return {} return {}
end end
local prev_entries = (function() local target_entries = (function()
local key = { 'get_entries', self.revision } local key = { 'get_entries', self.revision }
for i = ctx.cursor.col, self.offset, -1 do for i = ctx.cursor.col, self.offset, -1 do
key[3] = string.sub(ctx.cursor_before_line, 1, i) key[3] = string.sub(ctx.cursor_before_line, 1, i)
@@ -91,36 +91,27 @@ source.get_entries = function(self, ctx)
return prev_entries return prev_entries
end end
end end
return nil return self.entries
end)() end)()
local entries = self.cache:ensure({ 'get_entries', self.revision, ctx.cursor_before_line }, function()
debug.log(self:get_debug_name(), 'filter', #(prev_entries or self.entries))
local inputs = {} local inputs = {}
local entries = {} local entries = {}
for _, e in ipairs(prev_entries or self.entries) do for _, e in ipairs(target_entries) do
local o = e:get_offset() local o = e:get_offset()
if not inputs[o] then if not inputs[o] then
inputs[o] = string.sub(ctx.cursor_before_line, o) inputs[o] = string.sub(ctx.cursor_before_line, o)
end end
local score, matches = matcher.match(inputs[o], e:get_filter_text(), { e:get_word() })
e.score = score local match = e:match(inputs[o])
e.score = match.score
e.exact = false e.exact = false
if e.score >= 1 then if e.score >= 1 then
if e:get_filter_text() ~= e.completion_item.label then e.matches = match.matches
local _, matches_for_highlights = matcher.match(inputs[o], e.completion_item.label, {})
e.matches = matches_for_highlights
else
e.matches = matches
end
e.exact = e:get_filter_text() == inputs[o] or e:get_word() == inputs[o] e.exact = e:get_filter_text() == inputs[o] or e:get_word() == inputs[o]
table.insert(entries, e) table.insert(entries, e)
end end
end end
self.cache:set({ 'get_entries', self.revision, ctx.cursor_before_line }, entries)
return entries
end)
local max_item_count = self:get_config().max_item_count or 200 local max_item_count = self:get_config().max_item_count or 200
local limited_entries = {} local limited_entries = {}