aboutsummaryrefslogtreecommitdiff
path: root/runtime/lua/vim/lsp/buf.lua
diff options
context:
space:
mode:
authorRiley Bruins <ribru17@hotmail.com>2024-11-17 12:31:32 -0800
committerGitHub <noreply@github.com>2024-11-17 12:31:32 -0800
commit44229bb85b6cff00193164967126d85a7a785a7b (patch)
tree04a8b7cef4bbed61e43b6284c34bff9ed901cc00 /runtime/lua/vim/lsp/buf.lua
parent235cb5bc5f2553f5a46807267b8705e53f7a14af (diff)
downloadrneovim-44229bb85b6cff00193164967126d85a7a785a7b.tar.gz
rneovim-44229bb85b6cff00193164967126d85a7a785a7b.tar.bz2
rneovim-44229bb85b6cff00193164967126d85a7a785a7b.zip
feat(lsp): highlight hover target/range #31110
**Problem:** Despite the LSP providing the option for language servers to specify a range with a hover response (for highlighting), Neovim does not give the option to highlight this range. **Solution:** Add an option to `buf.hover()` which causes this range to be highlighted. Co-authored-by: Mathias Fußenegger <mfussenegger@users.noreply.github.com>
Diffstat (limited to 'runtime/lua/vim/lsp/buf.lua')
-rw-r--r--runtime/lua/vim/lsp/buf.lua45
1 files changed, 42 insertions, 3 deletions
diff --git a/runtime/lua/vim/lsp/buf.lua b/runtime/lua/vim/lsp/buf.lua
index 6d7597c5ff..a75e322e90 100644
--- a/runtime/lua/vim/lsp/buf.lua
+++ b/runtime/lua/vim/lsp/buf.lua
@@ -20,6 +20,8 @@ local function client_positional_params(params)
end
end
+local hover_ns = api.nvim_create_namespace('vim_lsp_hover_range')
+
--- @class vim.lsp.buf.hover.Opts : vim.lsp.util.open_floating_preview.Opts
--- @field silent? boolean
@@ -30,13 +32,24 @@ end
--- In the floating window, all commands and mappings are available as usual,
--- except that "q" dismisses the window.
--- You can scroll the contents the same as you would any other buffer.
+---
+--- Note: to disable hover highlights, add the following to your config:
+---
+--- ```lua
+--- vim.api.nvim_create_autocmd('ColorScheme', {
+--- callback = function()
+--- vim.api.nvim_set_hl(0, 'LspReferenceTarget', {})
+--- end,
+--- })
+--- ```
--- @param config? vim.lsp.buf.hover.Opts
function M.hover(config)
config = config or {}
config.focus_id = ms.textDocument_hover
lsp.buf_request_all(0, ms.textDocument_hover, client_positional_params(), function(results, ctx)
- if api.nvim_get_current_buf() ~= ctx.bufnr then
+ local bufnr = assert(ctx.bufnr)
+ if api.nvim_get_current_buf() ~= bufnr then
-- Ignore result since buffer changed. This happens for slow language servers.
return
end
@@ -67,9 +80,10 @@ function M.hover(config)
local format = 'markdown'
for client_id, result in pairs(results1) do
+ local client = assert(lsp.get_client_by_id(client_id))
if nresults > 1 then
-- Show client name if there are multiple clients
- contents[#contents + 1] = string.format('# %s', lsp.get_client_by_id(client_id).name)
+ contents[#contents + 1] = string.format('# %s', client.name)
end
if type(result.contents) == 'table' and result.contents.kind == 'plaintext' then
if #results1 == 1 then
@@ -87,6 +101,22 @@ function M.hover(config)
else
vim.list_extend(contents, util.convert_input_to_markdown_lines(result.contents))
end
+ local range = result.range
+ if range then
+ local start = range.start
+ local end_ = range['end']
+ local start_idx = util._get_line_byte_from_position(bufnr, start, client.offset_encoding)
+ local end_idx = util._get_line_byte_from_position(bufnr, end_, client.offset_encoding)
+
+ vim.hl.range(
+ bufnr,
+ hover_ns,
+ 'LspReferenceTarget',
+ { start.line, start_idx },
+ { end_.line, end_idx },
+ { priority = vim.hl.priorities.user }
+ )
+ end
contents[#contents + 1] = '---'
end
@@ -100,7 +130,16 @@ function M.hover(config)
return
end
- lsp.util.open_floating_preview(contents, format, config)
+ local _, winid = lsp.util.open_floating_preview(contents, format, config)
+
+ api.nvim_create_autocmd('WinClosed', {
+ pattern = tostring(winid),
+ once = true,
+ callback = function()
+ api.nvim_buf_clear_namespace(bufnr, hover_ns, 0, -1)
+ return true
+ end,
+ })
end)
end