Skip to content

Commit 1efdc8a

Browse files
committed
feat: complete rework
1 parent 451dd9e commit 1efdc8a

25 files changed

+2474
-637
lines changed

lua/blink/cmp/accept.lua

+102
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
local utils = {}
2+
3+
local function accept(item)
4+
local sources = require('blink.cmp.sources')
5+
local fuzzy = require('blink.cmp.fuzzy')
6+
7+
local text_edit = item.textEdit
8+
if text_edit ~= nil then
9+
-- Adjust the position of the text edit to be the current cursor position
10+
-- since the data might be outdated. We compare the cursor column position
11+
-- from when the items were fetched versus the current.
12+
-- hack: figure out a better way
13+
local offset = vim.api.nvim_win_get_cursor(0)[2] - item.cursor_column
14+
text_edit.range['end'].character = text_edit.range['end'].character + offset
15+
else
16+
-- No text edit so we fallback to our own resolution
17+
text_edit = utils.guess_text_edit(vim.api.nvim_get_current_buf(), item)
18+
end
19+
20+
-- Snippet
21+
if item.insertTextFormat == vim.lsp.protocol.InsertTextFormat.Snippet then
22+
-- We want to handle offset_encoding and the text edit api can do this for us
23+
-- so we empty the newText and apply
24+
local temp_text_edit = vim.deepcopy(text_edit)
25+
temp_text_edit.newText = ''
26+
utils.apply_text_edits(item.client_id, { temp_text_edit })
27+
28+
-- Expand the snippet
29+
-- todo: use the snippet plugin api
30+
vim.snippet.expand(text_edit.newText)
31+
else
32+
-- Apply the text edit and move the cursor
33+
utils.apply_text_edits(item.client_id, { text_edit })
34+
vim.api.nvim_win_set_cursor(
35+
0,
36+
{ text_edit.range.start.line + 1, text_edit.range.start.character + #text_edit.newText }
37+
)
38+
end
39+
40+
-- Apply additional text edits
41+
-- LSPs can either include these in the initial response or require a resolve
42+
-- These are used for things like auto-imports
43+
-- todo: check capabilities to know ahead of time
44+
if item.additionalTextEdits ~= nil then
45+
utils.apply_text_edits(item.client_id, item.additionalTextEdits)
46+
else
47+
sources.resolve(
48+
item,
49+
function(resolved_item) utils.apply_text_edits(item.client_id, resolved_item.additionalTextEdits or {}) end
50+
)
51+
end
52+
53+
-- Notify the rust module that the item was accessed
54+
fuzzy.access(item.label)
55+
end
56+
57+
---------- UTILS ------------
58+
59+
function utils.guess_text_edit(bufnr, item)
60+
local word = item.insertText or item.label
61+
62+
local current_line = vim.api.nvim_win_get_cursor(0)[1]
63+
local current_col = vim.api.nvim_win_get_cursor(0)[2]
64+
local line = vim.api.nvim_buf_get_lines(bufnr, current_line - 1, current_line, false)[1]
65+
66+
-- Search forward/backward for the start/end of the word
67+
local start_col = current_col
68+
while start_col > 1 do
69+
local char = line:sub(start_col, start_col)
70+
if char:match('[%w_\\-]') == nil then
71+
start_col = start_col + 1
72+
break
73+
end
74+
start_col = start_col - 1
75+
end
76+
77+
-- todo: dont search forward since LSPs dont typically do this so it will be inconsistent
78+
local end_col = current_col
79+
while end_col < #line do
80+
local char = line:sub(end_col + 1, end_col + 1)
81+
if char:match('[%w_\\-]') == nil then break end
82+
end_col = end_col + 1
83+
end
84+
85+
-- convert to 0-index
86+
return {
87+
range = {
88+
start = { line = current_line - 1, character = start_col - 1 },
89+
['end'] = { line = current_line - 1, character = end_col },
90+
},
91+
newText = word,
92+
}
93+
end
94+
95+
function utils.apply_text_edits(client_id, edits)
96+
local client = vim.lsp.get_client_by_id(client_id)
97+
vim.print(vim.inspect(client_id))
98+
local offset_encoding = client ~= nil and client.offset_encoding or 'utf-16'
99+
vim.lsp.util.apply_text_edits(edits, vim.api.nvim_get_current_buf(), offset_encoding)
100+
end
101+
102+
return accept

lua/blink/cmp/cmp.lua

-292
This file was deleted.

0 commit comments

Comments
 (0)