diff --git a/lua/outline/hover.lua b/lua/outline/hover.lua deleted file mode 100644 index b43aaa0..0000000 --- a/lua/outline/hover.lua +++ /dev/null @@ -1,42 +0,0 @@ -local cfg = require('outline.config') -local outline = require('outline') - -local M = {} - -local function get_hover_params(node, winnr) - local bufnr = vim.api.nvim_win_get_buf(winnr) - local fn = vim.uri_from_bufnr(bufnr) - - return { - textDocument = { uri = fn }, - position = { line = node.line, character = node.character }, - bufnr = bufnr, - } -end - -function M.show_hover() - local current_line = vim.api.nvim_win_get_cursor(outline.current.view.win)[1] - local node = outline.current.flats[current_line] - - local hover_params = get_hover_params(node, outline.current.code.win) - - vim.lsp.buf_request( - hover_params.bufnr, - 'textDocument/hover', - hover_params, - function(_, result, _, config) - if not (result and result.contents) then - return - end - local markdown_lines = vim.lsp.util.convert_input_to_markdown_lines(result.contents) - markdown_lines = vim.lsp.util.trim_empty_lines(markdown_lines) - if vim.tbl_isempty(markdown_lines) then - return - end - local bufnr, winnr = vim.lsp.util.open_floating_preview(markdown_lines, 'markdown', config) - vim.api.nvim_win_set_option(winnr, 'winhighlight', cfg.o.preview_window.winhl) - end - ) -end - -return M diff --git a/lua/outline/providers/coc.lua b/lua/outline/providers/coc.lua index 1d18fe6..47b725d 100644 --- a/lua/outline/providers/coc.lua +++ b/lua/outline/providers/coc.lua @@ -16,15 +16,6 @@ function M.supports_buffer(_) return coc_attached and has_symbols end -function M.hover_info(_, _, on_info) - on_info(nil, { - contents = { - kind = 'markdown', - contents = { 'No extra information availaible!' }, - }, - }) -end - ---@param result table local function convert_symbols(result) local s = {} diff --git a/lua/outline/providers/markdown.lua b/lua/outline/providers/markdown.lua index b5c5683..441f8c8 100644 --- a/lua/outline/providers/markdown.lua +++ b/lua/outline/providers/markdown.lua @@ -20,15 +20,6 @@ function M.supports_buffer(bufnr) return vim.api.nvim_buf_get_option(bufnr, 'ft') == 'markdown' end -function M.hover_info(_, _, on_info) - on_info(nil, { - contents = { - kind = 'markdown', - contents = { 'No extra information availaible!' }, - }, - }) -end - -- Parses markdown files and returns a table of SymbolInformation[] which is -- used by the plugin to show the outline. ---@return outline.ProviderSymbol[] diff --git a/lua/outline/providers/nvim-lsp.lua b/lua/outline/providers/nvim-lsp.lua index 95b03e7..5b482d9 100644 --- a/lua/outline/providers/nvim-lsp.lua +++ b/lua/outline/providers/nvim-lsp.lua @@ -1,13 +1,17 @@ -local config = require('outline.config') +local cfg = require('outline.config') local jsx = require('outline.providers.jsx') local lsp_utils = require('outline.utils.lsp') +local l = vim.lsp + local M = { name = 'lsp', - ---@type vim.lsp.client + ---@type lsp.client client = nil, } +local request_timeout = 2000 + function M.get_status() if not M.client then return { 'No clients' } @@ -16,11 +20,11 @@ function M.get_status() end local function get_appropriate_client(bufnr, capability) - local clients = vim.lsp.get_active_clients({ bufnr = bufnr }) + local clients = l.get_active_clients({ bufnr = bufnr }) local use_client for _, client in ipairs(clients) do - if config.is_client_blacklisted(client) then + if cfg.is_client_blacklisted(client) then goto continue else if client.server_capabilities[capability] then @@ -61,9 +65,9 @@ end ---@param opts table function M.request_symbols(on_symbols, opts) local params = { - textDocument = vim.lsp.util.make_text_document_params(), + textDocument = l.util.make_text_document_params(), } - vim.lsp.buf_request_all(0, 'textDocument/documentSymbol', params, function(response) + l.buf_request_all(0, 'textDocument/documentSymbol', params, function(response) response = postprocess_symbols(response) on_symbols(response, opts) end) @@ -86,7 +90,7 @@ function M.code_actions(sidebar) -- we still keep it because many people are moving here from -- symbols-outline.nvim, which happened to implement this feature. sidebar:wrap_goto_location(function() - vim.lsp.buf.code_action() + l.buf.code_action() end) return true end @@ -114,32 +118,51 @@ function M.rename_symbol(sidebar) bufnr = sidebar.code.buf, newName = new_name, } - local timeout = 2000 - local status, err = client.request_sync('textDocument/rename', params, timeout, sidebar.code.buf) + local status, err = client.request_sync('textDocument/rename', params, request_timeout, sidebar.code.buf) if status == nil or status.err or err or status.result == nil then return false end - vim.lsp.util.apply_workspace_edit(status.result, client.offset_encoding) + l.util.apply_workspace_edit(status.result, client.offset_encoding) node.name = new_name sidebar:_update_lines(false) return true end -function M.hover_info(bufnr, params, on_info) - local use_client = get_appropriate_client(bufnr, 'hoverProvider') - - if not use_client then - on_info(nil, { - contents = { - kind = 'markdown', - content = { 'No extra information availaible' }, - }, - }) - return +---Synchronously request and show hover info from LSP +---@param sidebar outline.Sidebar +---@return boolean success +function M.show_hover(sidebar) + local client = get_appropriate_client(sidebar.code.buf, 'hoverProvider') + if not client then + return false end - use_client.request('textDocument/hover', params, on_info, bufnr) + local node = sidebar:_current_node() + local params = { + textDocument = { uri = vim.uri_from_bufnr(sidebar.code.buf) }, + position = { line = node.line, character = node.character }, + bufnr = sidebar.code.buf, + } + + local status, err = client.request_sync('textDocument/hover', params, request_timeout) + if status == nil or status.err or err or not status.result or not status.result.contents then + return false + end + + local md_lines = l.util.convert_input_to_markdown_lines(status.result.contents) + md_lines = l.util.trim_empty_lines(md_lines) + if vim.tbl_isempty(md_lines) then + -- Request was successful, but there is no hover content + return true + end + local code_width = vim.api.nvim_win_get_width(sidebar.code.win) + local bufnr, winnr = l.util.open_floating_preview(md_lines, 'markdown', { + border = cfg.o.preview_window.border, + width = code_width, + }) + vim.api.nvim_win_set_option(winnr, 'winhighlight', cfg.o.preview_window.winhl) + return true end return M diff --git a/lua/outline/sidebar.lua b/lua/outline/sidebar.lua index 192bf43..fb4bd05 100644 --- a/lua/outline/sidebar.lua +++ b/lua/outline/sidebar.lua @@ -147,13 +147,15 @@ function Sidebar:setup_keymaps() fold_all = { '_set_all_folded', { true } }, unfold_all = { '_set_all_folded', { false } }, fold_reset = { '_set_all_folded', {} }, - hover_symbol = { require('outline.hover').show_hover, {} }, rename_symbol = { providers.action, { self, 'rename_symbol', { self } } }, code_actions = { providers.action, { self, 'code_actions', { self } } }, + hover_symbol = { + providers.action, { self, 'show_hover', { self } } + }, }) do ---@diagnostic disable-next-line param-type-mismatch self:nmap(name, meth[1], meth[2]) diff --git a/lua/outline/types/outline.lua b/lua/outline/types/outline.lua index 9e90cac..ecc8578 100644 --- a/lua/outline/types/outline.lua +++ b/lua/outline/types/outline.lua @@ -66,7 +66,7 @@ ---@field get_status? fun():string[] ---@field supports_buffer fun(bufnr:integer):boolean ---@field request_symbols fun(on_symbols:fun(symbols?:outline.ProviderSymbol[], opts:table?), opts:table?) ----@field hover_info? fun(bufnr:integer, params:table, on_info:function) +---@field show_hover? fun(sidebar:outline.Sidebar):boolean ---@field rename_symbol? fun(sidebar:outline.Sidebar):boolean ---@field code_actions? fun(sidebar:outline.Sidebar):boolean