diff options
author | Folke Lemaitre <folke.lemaitre@gmail.com> | 2021-07-09 12:38:29 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-07-09 03:38:29 -0700 |
commit | 9132b76da6c22bdd96af62113ff23e408fcc2ae7 (patch) | |
tree | dcf57bfac808ff6afff527def052895c3b21908d /runtime/lua/vim | |
parent | 1c416892879de6b78038f2cc2f1487eff46abb60 (diff) | |
download | rneovim-9132b76da6c22bdd96af62113ff23e408fcc2ae7.tar.gz rneovim-9132b76da6c22bdd96af62113ff23e408fcc2ae7.tar.bz2 rneovim-9132b76da6c22bdd96af62113ff23e408fcc2ae7.zip |
fix(lsp): support duplicate params in signature help (#15032)
Diffstat (limited to 'runtime/lua/vim')
-rw-r--r-- | runtime/lua/vim/lsp/handlers.lua | 14 | ||||
-rw-r--r-- | runtime/lua/vim/lsp/util.lua | 32 |
2 files changed, 37 insertions, 9 deletions
diff --git a/runtime/lua/vim/lsp/handlers.lua b/runtime/lua/vim/lsp/handlers.lua index 7da24d8c43..d39107a01f 100644 --- a/runtime/lua/vim/lsp/handlers.lua +++ b/runtime/lua/vim/lsp/handlers.lua @@ -329,20 +329,26 @@ M['textDocument/implementation'] = location_handler --- - border: (default=nil) --- - Add borders to the floating window --- - See |vim.api.nvim_open_win()| -function M.signature_help(_, method, result, _, bufnr, config) +function M.signature_help(_, method, result, client_id, bufnr, config) config = config or {} config.focus_id = method -- When use `autocmd CompleteDone <silent><buffer> lua vim.lsp.buf.signature_help()` to call signatureHelp handler -- If the completion item doesn't have signatures It will make noise. Change to use `print` that can use `<silent>` to ignore if not (result and result.signatures and result.signatures[1]) then - print('No signature help available') + if config.silent ~= true then + print('No signature help available') + end return end + local client = vim.lsp.get_client_by_id(client_id) + local triggers = client.resolved_capabilities.signature_help_trigger_characters local ft = api.nvim_buf_get_option(bufnr, 'filetype') - local lines, hl = util.convert_signature_help_to_markdown_lines(result, ft) + local lines, hl = util.convert_signature_help_to_markdown_lines(result, ft, triggers) lines = util.trim_empty_lines(lines) if vim.tbl_isempty(lines) then - print('No signature help available') + if config.silent ~= true then + print('No signature help available') + end return end local fbuf, fwin = util.open_floating_preview(lines, "markdown", config) diff --git a/runtime/lua/vim/lsp/util.lua b/runtime/lua/vim/lsp/util.lua index 17440ca1b5..f047a12dff 100644 --- a/runtime/lua/vim/lsp/util.lua +++ b/runtime/lua/vim/lsp/util.lua @@ -845,9 +845,10 @@ end --- --@param signature_help Response of `textDocument/SignatureHelp` --@param ft optional filetype that will be use as the `lang` for the label markdown code block +--@param triggers optional list of trigger characters from the lsp server. used to better determine parameter offsets --@returns list of lines of converted markdown. --@see https://microsoft.github.io/language-server-protocol/specifications/specification-current/#textDocument_signatureHelp -function M.convert_signature_help_to_markdown_lines(signature_help, ft) +function M.convert_signature_help_to_markdown_lines(signature_help, ft, triggers) if not signature_help.signatures then return end @@ -877,10 +878,16 @@ function M.convert_signature_help_to_markdown_lines(signature_help, ft) end if signature.parameters and #signature.parameters > 0 then local active_parameter = (signature.activeParameter or signature_help.activeParameter or 0) - -- If the activeParameter is not inside the valid range, then clip it. + if active_parameter < 0 + then active_parameter = 0 + end + + -- If the activeParameter is > #parameters, then set it to the last + -- NOTE: this is not fully according to the spec, but a client-side interpretation if active_parameter >= #signature.parameters then - active_parameter = 0 + active_parameter = #signature.parameters - 1 end + local parameter = signature.parameters[active_parameter + 1] if parameter then --[=[ @@ -905,8 +912,23 @@ function M.convert_signature_help_to_markdown_lines(signature_help, ft) if type(parameter.label) == "table" then active_hl = parameter.label else - local i = signature.label:find(parameter.label) - if i then active_hl = {i - 1, i + #parameter.label - 1} end + local offset = 1 + -- try to set the initial offset to the first found trigger character + for _, t in ipairs(triggers or {}) do + local trigger_offset = signature.label:find(t, 1, true) + if trigger_offset and (offset == 1 or trigger_offset < offset) then + offset = trigger_offset + end + end + for p, param in pairs(signature.parameters) do + offset = signature.label:find(param.label, offset, true) + if not offset then break end + if p == active_parameter + 1 then + active_hl = {offset - 1, offset + #parameter.label - 1} + break + end + offset = offset + #param.label + 1 + end end end if parameter.documentation then |