forked from Archives/navigator.lua
Compare commits
66 Commits
Author | SHA1 | Date | |
---|---|---|---|
|
cd98ca2c5b | ||
|
451d761f76 | ||
|
8278f71878 | ||
|
443fd4d585 | ||
|
10fd76d6d0 | ||
|
8d00282020 | ||
|
9afcd37854 | ||
|
c70d032b08 | ||
|
fb6d19ddf4 | ||
|
af7fc7d649 | ||
|
d8f19f6fc1 | ||
|
df7f4d7229 | ||
|
fb87a0b1b7 | ||
|
927c464b70 | ||
|
e9a40aca40 | ||
|
edee3e39c6 | ||
|
a7886fc055 | ||
|
de018d9ae3 | ||
|
ef0cee5bbd | ||
|
ab2e383b20 | ||
|
1b262556c0 | ||
|
b4ff1c43b9 | ||
|
ebd88f5d09 | ||
|
28d245510f | ||
|
213b30950e | ||
|
f05d2ec142 | ||
|
9f151cf718 | ||
|
b131251ad8 | ||
|
8978bdb1e3 | ||
|
ae251289b3 | ||
|
a9c223cc22 | ||
|
0ab4b02ff7 | ||
|
6c0e286170 | ||
|
f24a337f5d | ||
|
3d87ed3b87 | ||
|
5713f79265 | ||
|
01ef2ce1a1 | ||
|
547f2bc15d | ||
|
dc0b8504bb | ||
|
486085070d | ||
|
bc356d555f | ||
|
5b5a946d73 | ||
|
fca2fa5aaa | ||
|
49dbca889d | ||
|
861ae038dd | ||
|
814b712e91 | ||
|
dcc40278c5 | ||
|
6736293182 | ||
|
10ef469286 | ||
|
4775d43218 | ||
|
89dd02c927 | ||
|
bbdf86a66e | ||
|
ed47d386e6 | ||
|
480824d3f3 | ||
|
c3ef990390 | ||
|
de5c88c766 | ||
|
348ab9dced | ||
|
967fd32bae | ||
|
4aef8dc5f2 | ||
|
0de6c290cf | ||
|
9aad2978dc | ||
|
49c3e5cd4d | ||
|
47545e03c0 | ||
|
e5d16e4488 | ||
|
3d9a9582dd | ||
|
05dfed9ed9 |
4
.github/workflows/ci.yml
vendored
4
.github/workflows/ci.yml
vendored
@ -15,11 +15,11 @@ jobs:
|
||||
manager: sudo snap
|
||||
packages: go
|
||||
- os: ubuntu-22.04
|
||||
url: https://github.com/neovim/neovim/releases/download/v0.7.2/nvim-linux64.tar.gz
|
||||
url: https://github.com/neovim/neovim/releases/download/v0.7.0/nvim-linux64.tar.gz
|
||||
manager: sudo snap
|
||||
packages: go
|
||||
- os: ubuntu-22.04
|
||||
url: https://github.com/neovim/neovim/releases/download/v0.6.1/nvim-linux64.tar.gz
|
||||
url: https://github.com/neovim/neovim/releases/download/v0.7.2/nvim-linux64.tar.gz
|
||||
manager: sudo snap
|
||||
packages: go
|
||||
steps:
|
||||
|
2
.gitignore
vendored
2
.gitignore
vendored
@ -1,3 +1,3 @@
|
||||
|
||||
selene.toml
|
||||
lua/navigator.lua.bak
|
||||
tests/fixtures/tests
|
134
README.md
134
README.md
@ -257,12 +257,14 @@ require'navigator'.setup({
|
||||
-- end,
|
||||
-- The attach code will apply to all LSP clients
|
||||
|
||||
ts_fold = false, -- modified version of treesitter folding
|
||||
default_mapping = true, -- set to false if you will remap every key or if you using old version of nvim-
|
||||
keymaps = {{key = "gK", func = vim.lsp.declaration, desc = 'declaration'}}, -- a list of key maps
|
||||
-- this kepmap gK will override "gD" mapping function declaration() in default kepmap
|
||||
-- please check mapping.lua for all keymaps
|
||||
treesitter_analysis = true, -- treesitter variable context
|
||||
treesitter_analysis_max_num = 100, -- how many items to run treesitter analysis
|
||||
treesitter_analysis_condense = true, -- condense form for treesitter analysis
|
||||
-- this value prevent slow in large projects, e.g. found 100000 reference in a project
|
||||
transparency = 50, -- 0 ~ 100 blur the main window, 100: fully transparent, 0: opaque, set to nil or 100 to disable it
|
||||
|
||||
@ -278,18 +280,23 @@ require'navigator'.setup({
|
||||
-- refer to lua/navigator.lua for more icons setups
|
||||
},
|
||||
lsp_installer = false, -- set to true if you would like use the lsp installed by williamboman/nvim-lsp-installer
|
||||
mason = false, -- set to true if you would like use the lsp installed by williamboman/mason
|
||||
lsp = {
|
||||
enable = true, -- skip lsp setup if disabled make sure add require('navigator.lspclient.mapping').setup() in you
|
||||
-- own on_attach
|
||||
code_action = {enable = true, sign = true, sign_priority = 40, virtual_text = true},
|
||||
code_lens_action = {enable = true, sign = true, sign_priority = 40, virtual_text = true},
|
||||
document_highlight = true, -- LSP reference highlight,
|
||||
-- it might already supported by you setup, e.g. LunarVim
|
||||
format_on_save = true, -- set to false to disable lsp code format on save (if you are using prettier/efm/formater etc)
|
||||
format_options = {async=false}, -- async: disable by default, the option used in vim.lsp.buf.format({async={true|false}, name = 'xxx'})
|
||||
disable_format_cap = {"sqls", "sumneko_lua", "gopls"}, -- a list of lsp disable format capacity (e.g. if you using efm or vim-codeformat etc), empty {} by default
|
||||
-- If you using null-ls and want null-ls format your code
|
||||
-- you should disable all other lsp and allow only null-ls.
|
||||
disable_lsp = {'pylsd', 'sqlls'}, -- a list of lsp server disabled for your project, e.g. denols and tsserver you may
|
||||
-- only want to enable one lsp server
|
||||
--want to enable one lsp server at a time
|
||||
-- to disable all default config and use your own lsp setup set
|
||||
-- disable_lsp = 'all'
|
||||
-- disable_lsp = 'all' and you may need to hook mapping.setup() in your on_attach
|
||||
-- Default {}
|
||||
diagnostic = {
|
||||
underline = true,
|
||||
@ -309,9 +316,9 @@ require'navigator'.setup({
|
||||
},
|
||||
ctags ={
|
||||
cmd = 'ctags',
|
||||
tagfile = 'tags'
|
||||
options = '-R --exclude=.git --exclude=node_modules --exclude=test --exclude=vendor --excmd=number'
|
||||
}
|
||||
tagfile = 'tags',
|
||||
options = '-R --exclude=.git --exclude=node_modules --exclude=test --exclude=vendor --excmd=number',
|
||||
},
|
||||
gopls = { -- gopls setting
|
||||
on_attach = function(client, bufnr) -- on_attach for gopls
|
||||
-- your special on attach here
|
||||
@ -323,6 +330,18 @@ require'navigator'.setup({
|
||||
gopls = {gofumpt = false} -- disable gofumpt etc,
|
||||
}
|
||||
},
|
||||
-- the lsp setup can be a function, .e.g
|
||||
gopls = function()
|
||||
local go = pcall(require, "go")
|
||||
if go then
|
||||
local cfg = require("go.lsp").config()
|
||||
cfg.on_attach = function(client)
|
||||
client.server_capabilities.documentFormattingProvider = false -- efm/null-ls
|
||||
end
|
||||
return cfg
|
||||
end
|
||||
end,
|
||||
|
||||
sumneko_lua = {
|
||||
sumneko_root_path = vim.fn.expand("$HOME") .. "/github/sumneko/lua-language-server",
|
||||
sumneko_binary = vim.fn.expand("$HOME") .. "/github/sumneko/lua-language-server/bin/macOS/lua-language-server",
|
||||
@ -430,7 +449,7 @@ In `playground` folder, there is a `init.lua` and source code for you to play wi
|
||||
| n | gd | definition |
|
||||
| n | g0 | document symbol |
|
||||
| n | \<C-]\> | go to definition (if multiple show listview) |
|
||||
| n | gp | definition preview (Go to Preview) |
|
||||
| n | gp | definition preview (show Preview) |
|
||||
| n | \<C-LeftMouse\> | definition |
|
||||
| n | g\<LeftMouse\> | implementation |
|
||||
| n | \<Leader>gt | treesitter document symbol |
|
||||
@ -471,20 +490,21 @@ In `playground` folder, there is a `init.lua` and source code for you to play wi
|
||||
| n | \<Enter\> | open preview file in nvim/Apply action |
|
||||
| n | \<ESC\> | close listview of floating window |
|
||||
| i/n | \<C-e\> | close listview of floating window |
|
||||
| n | \<C-q\> | close listview and send results to quickfix |
|
||||
| i/n | \<C-b\> | previous page in listview |
|
||||
| i/n | \<C-f\> | next page in listview |
|
||||
| i/n | \<C-s\> | save the modification to preview window to file |
|
||||
|
||||
### Colors/Highlight:
|
||||
|
||||
You can override default highlight GHListDark (listview) and GHTextViewDark (code view) and GHListHl (select item)
|
||||
You can override default highlight GuihuaListDark (listview) and GuihuaTextViewDark (code view) and GuihuaListHl (select item)
|
||||
|
||||
e.g.
|
||||
|
||||
```vim
|
||||
hi default GHTextViewDark guifg=#e0d8f4 guibg=#332e55
|
||||
hi default GHListDark guifg=#e0d8f4 guibg=#103234
|
||||
hi default GHListHl guifg=#e0d8f4 guibg=#404254
|
||||
hi default GuihuaTextViewDark guifg=#e0d8f4 guibg=#332e55
|
||||
hi default GuihuaListDark guifg=#e0d8f4 guibg=#103234
|
||||
hi default GuihuaListHl guifg=#e0d8f4 guibg=#404254
|
||||
```
|
||||
|
||||
There are other Lsp highlight been used in this plugin, e.g LspReferenceRead/Text/Write are used for document highlight,
|
||||
@ -502,18 +522,18 @@ The plugin can be loaded lazily (packer `opt = true` ), And it will check if opt
|
||||
|
||||
The terminal will need to be able to output nerdfont and emoji correctly. I am using Kitty with nerdfont (Victor Mono).
|
||||
|
||||
## Integrat with lsp_installer (williamboman/nvim-lsp-installer)
|
||||
## Integrat with mason (williamboman/mason.nvim) or lsp_installer (williamboman/nvim-lsp-installer, deprecated)
|
||||
|
||||
If you are using lsp_installer and would like to use the lsp servers installed by lsp_installer. Please set
|
||||
If you are using mason or lsp_installer and would like to use the lsp servers installed by lsp_installer. Please set
|
||||
|
||||
```lua
|
||||
lsp_installer = true
|
||||
|
||||
lsp_installer = true --lsp_installer users, deprecated
|
||||
mason = true -- mason user
|
||||
```
|
||||
|
||||
In the config. Also please setup the lsp server from installer setup with `server:setup{opts}`
|
||||
|
||||
example:
|
||||
lsp-installer example:
|
||||
```lua
|
||||
use({
|
||||
'williamboman/nvim-lsp-installer',
|
||||
@ -526,14 +546,79 @@ example:
|
||||
'ray-x/navigator.lua',
|
||||
config = function()
|
||||
require('navigator').setup({
|
||||
debug = true,
|
||||
lsp_installer = true,
|
||||
keymaps = { { key = 'gR', func = "require('navigator.reference').async_ref()" } },
|
||||
})
|
||||
end,
|
||||
})
|
||||
|
||||
```
|
||||
for mason
|
||||
```lua
|
||||
use("williamboman/mason.nvim")
|
||||
use({
|
||||
"williamboman/mason-lspconfig.nvim",
|
||||
config = function()
|
||||
require("mason").setup()
|
||||
require("mason-lspconfig").setup({})
|
||||
end,
|
||||
})
|
||||
|
||||
use({
|
||||
"ray-x/navigator.lua",
|
||||
requires = {
|
||||
{ "ray-x/guihua.lua", run = "cd lua/fzy && make" },
|
||||
{ "neovim/nvim-lspconfig" },
|
||||
{ "nvim-treesitter/nvim-treesitter" },
|
||||
},
|
||||
config = function()
|
||||
require("navigator").setup({
|
||||
mason = true,
|
||||
})
|
||||
end,
|
||||
})
|
||||
|
||||
```
|
||||
|
||||
Another way to setup mason is disable navigator lsp setup and using mason setup handlers, pylsp for example
|
||||
|
||||
```lua
|
||||
use("williamboman/mason.nvim")
|
||||
use({
|
||||
"williamboman/mason-lspconfig.nvim",
|
||||
config = function()
|
||||
require("mason").setup()
|
||||
require("mason-lspconfig").setup_handlers({
|
||||
["pylsp"] = function()
|
||||
require("lspconfig").pylsp.setup({
|
||||
on_attach = function(client, bufnr)
|
||||
require("navigator.lspclient.mapping").setup({ client = client, bufnr = bufnr }) -- setup navigator keymaps here,
|
||||
require("navigator.dochighlight").documentHighlight(bufnr)
|
||||
require("navigator.codeAction").code_action_prompt(bufnr)
|
||||
end,
|
||||
})
|
||||
end,
|
||||
})
|
||||
require("mason-lspconfig").setup({})
|
||||
end,
|
||||
})
|
||||
|
||||
use({
|
||||
"navigator.lua",
|
||||
requires = {
|
||||
{ "ray-x/guihua.lua", run = "cd lua/fzy && make" },
|
||||
{ "nvim-lspconfig" },
|
||||
{ "nvim-treesitter/nvim-treesitter" },
|
||||
},
|
||||
config = function()
|
||||
require("navigator").setup({
|
||||
mason = true,
|
||||
lsp = { disable_lsp = { "pylsp" } }, -- disable pylsp setup from navigator
|
||||
})
|
||||
end,
|
||||
})
|
||||
|
||||
```
|
||||
|
||||
|
||||
Please refer to [lsp_installer_config](https://github.com/ray-x/navigator.lua/blob/master/playground/init_lsp_installer.lua)
|
||||
for more info
|
||||
@ -549,7 +634,9 @@ To start LSP installed by lsp_installer, please use following setups
|
||||
require'navigator'.setup({
|
||||
-- lsp_installer = false -- default value is false
|
||||
lsp = {
|
||||
tsserver = { cmd = {'your tsserver installed by lsp_installer'} }
|
||||
tsserver = { cmd = {'your tsserver installed by lsp_installer or mason'} }
|
||||
-- e.g. tsserver = { cmd = {'/home/username/.local/share/nvim/mason/packages/typescript-language-server/node_modules/typescript/bin/tsserver'} }
|
||||
|
||||
}
|
||||
})
|
||||
|
||||
@ -564,6 +651,7 @@ require'navigator'.setup({
|
||||
lsp = {
|
||||
tsserver = {
|
||||
cmd = { "/Users/username/.local/share/nvim/lsp_servers/python/node_modules/.bin/pyright-langserver", "--stdio" }
|
||||
-- or mason: cmd = { "/Users/username/.local/share/nvim/mason/packages/pyright/node_modules/pyright/index.js", "--stdio"}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -623,6 +711,9 @@ require('rust-tools').setup({
|
||||
server = {
|
||||
on_attach = function(client, bufnr)
|
||||
require('navigator.lspclient.mapping').setup({client=client, bufnr=bufnr}) -- setup navigator keymaps here,
|
||||
|
||||
require("navigator.dochighlight").documentHighlight(bufnr)
|
||||
require('navigator.codeAction').code_action_prompt(bufnr)
|
||||
-- otherwise, you can define your own commands to call navigator functions
|
||||
end,
|
||||
}
|
||||
@ -632,6 +723,8 @@ require("clangd_extensions").setup {
|
||||
server = {
|
||||
on_attach = function(client, bufnr)
|
||||
require('navigator.lspclient.mapping').setup({client=client, bufnr=bufnr}) -- setup navigator keymaps here,
|
||||
require("navigator.dochighlight").documentHighlight(bufnr)
|
||||
require('navigator.codeAction').code_action_prompt(bufnr)
|
||||
-- otherwise, you can define your own commands to call navigator functions
|
||||
end,
|
||||
}
|
||||
@ -667,7 +760,7 @@ Highlight I am using:
|
||||
- LspReferenceRead, LspReferenceText and LspReferenceWrite are used for `autocmd CursorHold <buffer> lua vim.lsp.buf.document_highlight()`
|
||||
That is where you saw the current symbol been highlighted.
|
||||
|
||||
- GHListDark and GHTextViewDark is used for floating listvew and TextView. They are be based on current background
|
||||
- GuihuaListDark and GuihuaTextViewDark is used for floating listvew and TextView. They are be based on current background
|
||||
(Normal) and PmenuSel
|
||||
|
||||
- In future, I will use NormalFloat for floating view. But ATM, most of colorscheme does not define NormalFloat
|
||||
@ -684,6 +777,7 @@ You can override the above highlight to fit your current colorscheme
|
||||
| LspRestart | reload lsp |
|
||||
| LspToggleFmt | toggle lsp format |
|
||||
| LspSymbols | document symbol in side panel |
|
||||
| NRefPanel | show symbol reference in side panel |
|
||||
| TSymobls | treesitter symbol in side panel |
|
||||
| Calltree {args} | lsp call hierarchy call tree, args: -i (incomming default), -o (outgoing) |
|
||||
|
||||
@ -823,7 +917,7 @@ Codelens for C++/ccls. Symbol reference
|
||||
|
||||
### VS-code style folding with treesitter
|
||||
|
||||
Folding is using a hacked version of treesitter folding.
|
||||
Folding is using a hacked version of treesitter folding. (option: ts_fold)
|
||||
|
||||
#### folding function
|
||||
|
||||
|
@ -477,13 +477,13 @@ DEFAULT KEYMAPS *navigator-default_keymap
|
||||
|
||||
COLORS/HIGHLIGHT: *navigator-colors/highlight:*
|
||||
|
||||
You can override default highlight GHListDark (listview) and GHTextViewDark (code view) and GHListHl (select item)
|
||||
You can override default highlight GuihuaListDark (listview) and GuihuaTextViewDark (code view) and GuihuaListHl (select item)
|
||||
|
||||
e.g.
|
||||
>
|
||||
hi default GHTextViewDark guifg=#e0d8f4 guibg=#332e55
|
||||
hi default GHListDark guifg=#e0d8f4 guibg=#103234
|
||||
hi default GHListHl guifg=#e0d8f4 guibg=#404254
|
||||
hi default GuihuaTextViewDark guifg=#e0d8f4 guibg=#332e55
|
||||
hi default GuihuaListDark guifg=#e0d8f4 guibg=#103234
|
||||
hi default GuihuaListHl guifg=#e0d8f4 guibg=#404254
|
||||
<
|
||||
|
||||
There are other Lsp highlight been used in this plugin, e.g LspReferenceRead/Text/Write are used for document highlight,
|
||||
@ -644,7 +644,7 @@ Highlight I am using:
|
||||
|
||||
* LspReferenceRead, LspReferenceText and LspReferenceWrite are used for `autocmd CursorHold <buffer> lua vim.lsp.buf.document_highlight()`
|
||||
That is where you saw the current symbol been highlighted.
|
||||
* GHListDark and GHTextViewDark is used for floating listvew and TextView. They are be based on current background
|
||||
* GuihuaListDark and GuihuaTextViewDark is used for floating listvew and TextView. They are be based on current background
|
||||
(Normal) and PmenuSel
|
||||
* In future, I will use NormalFloat for floating view. But ATM, most of colorscheme does not define NormalFloat
|
||||
|
||||
@ -660,8 +660,9 @@ COMMANDS *navigator-command
|
||||
| Nctags {args} | show ctags symbols, args: -g regen ctags |
|
||||
| LspRestart | reload lsp |
|
||||
| LspSymbols | document symbol in side panel |
|
||||
| NRefPanel |symbol reference in side panel |
|
||||
| TSymobls | treesitter symbol in side panel |
|
||||
| CallTree {args} | lsp call hierarchy call tree, args: -i (incomming default), -o (outgoing) |
|
||||
| Calltree {args} | lsp call hierarchy call tree, args: -i (incomming default), -o (outgoing) |
|
||||
|
||||
:LspToggleFmt *:LspToggleFmt*
|
||||
Toggle lsp auto format.
|
||||
@ -683,6 +684,9 @@ COMMANDS *navigator-command
|
||||
:TSSymbols *:TSSymbols*
|
||||
Treesitter symbol in side panel.
|
||||
|
||||
:NRefPanel *:NRefPanel*
|
||||
Symbol reference in side panel.
|
||||
|
||||
:Calltree [flags] *:Calltree*
|
||||
Lsp call hierarchy call tree.
|
||||
[flags]:
|
||||
|
@ -1,12 +1,13 @@
|
||||
local M = {}
|
||||
local api = vim.api
|
||||
|
||||
local function warn(msg)
|
||||
vim.api.nvim_echo({ { 'WRN: ' .. msg, 'WarningMsg' } }, true, {})
|
||||
api.nvim_echo({ { 'WRN: ' .. msg, 'WarningMsg' } }, true, {})
|
||||
end
|
||||
|
||||
local function info(msg)
|
||||
if _NgConfigValues.debug then
|
||||
vim.api.nvim_echo({ { 'Info: ' .. msg } }, true, {})
|
||||
api.nvim_echo({ { 'Info: ' .. msg } }, true, {})
|
||||
end
|
||||
end
|
||||
|
||||
@ -31,11 +32,16 @@ _NgConfigValues = {
|
||||
ts_fold = false,
|
||||
treesitter_analysis = true, -- treesitter variable context
|
||||
treesitter_analysis_max_num = 100, -- how many items to run treesitter analysis
|
||||
treesitter_analysis_condense = true, -- short format of function
|
||||
transparency = 50, -- 0 ~ 100 blur the main window, 100: fully transparent, 0: opaque, set to nil to disable it
|
||||
lsp_signature_help = true, -- if you would like to hook ray-x/lsp_signature plugin in navigator
|
||||
-- setup here. if it is nil, navigator will not init signature help
|
||||
signature_help_cfg = { debug = false }, -- if you would like to init ray-x/lsp_signature plugin in navigator, pass in signature help
|
||||
ctags = { cmd = 'ctags', tagfile = '.tags' },
|
||||
ctags = {
|
||||
cmd = 'ctags',
|
||||
tagfile = '.tags',
|
||||
options = '-R --exclude=.git --exclude=node_modules --exclude=test --exclude=vendor --excmd=number',
|
||||
},
|
||||
lsp = {
|
||||
enable = true, -- if disabled make sure add require('navigator.lspclient.mapping').setup() in you on_attach
|
||||
code_action = {
|
||||
@ -45,6 +51,7 @@ _NgConfigValues = {
|
||||
virtual_text = true,
|
||||
virtual_text_icon = true,
|
||||
},
|
||||
document_highlight = true, -- highlight reference a symbol
|
||||
code_lens_action = {
|
||||
enable = true,
|
||||
sign = true,
|
||||
@ -86,6 +93,7 @@ _NgConfigValues = {
|
||||
servers = {}, -- you can add additional lsp server so navigator will load the default for you
|
||||
},
|
||||
lsp_installer = false, -- set to true if you would like use the lsp installed by williamboman/nvim-lsp-installer
|
||||
mason = false, -- set to true if you would like use the lsp installed by williamboman/mason
|
||||
icons = {
|
||||
icons = true, -- set to false to use system default ( if you using a terminal does not have nerd/icon)
|
||||
-- Code action
|
||||
@ -208,7 +216,7 @@ local extend_config = function(opts)
|
||||
else
|
||||
if _NgConfigValues[key][k] == nil then
|
||||
if key == 'lsp' then
|
||||
local lsp = require('navigator.lspclient.clients').lsp
|
||||
local lsp = require('navigator.lspclient.servers')
|
||||
if not vim.tbl_contains(lsp or {}, k) and k ~= 'efm' and k ~= 'null-ls' then
|
||||
info(string.format('[] extend LSP support for %s %s ', key, k))
|
||||
end
|
||||
@ -243,7 +251,14 @@ M.setup = function(cfg)
|
||||
cfg = cfg or {}
|
||||
extend_config(cfg)
|
||||
|
||||
vim.cmd([[autocmd FileType,BufEnter * lua require'navigator.lspclient.clients'.on_filetype()]]) -- BufWinEnter BufNewFile,BufRead ?
|
||||
local cmd_group = api.nvim_create_augroup('NGFtGroup', {})
|
||||
api.nvim_create_autocmd({ 'FileType', 'BufEnter' }, {
|
||||
group = cmd_group,
|
||||
pattern = '*',
|
||||
callback = function()
|
||||
require('navigator.lspclient.clients').on_filetype()
|
||||
end,
|
||||
})
|
||||
require('navigator.lazyloader').init()
|
||||
require('navigator.lspclient.clients').setup(_NgConfigValues)
|
||||
|
||||
@ -271,7 +286,6 @@ M.setup = function(cfg)
|
||||
local _start_client = vim.lsp.start_client
|
||||
vim.lsp.start_client = function(lsp_config)
|
||||
-- add highlight for Lspxxx
|
||||
require('navigator.dochighlight').documentHighlight()
|
||||
require('navigator.lspclient.highlight').add_highlight()
|
||||
require('navigator.lspclient.highlight').diagnositc_config_sign()
|
||||
-- require('navigator.lspclient.mapping').setup()
|
||||
|
@ -152,9 +152,13 @@ local code_action_req = function(_call_back_fn, diagnostics)
|
||||
end
|
||||
|
||||
local function sort_select(action_tuples, opts, on_user_choice)
|
||||
-- table.sort(action_tuples, function(a, b)
|
||||
-- return a[1] > b[1]
|
||||
-- end)
|
||||
if action_tuples ~= nil and action_tuples[1][2] ~= nil and action_tuples[1][2].command then
|
||||
table.sort(action_tuples, function(a, b)
|
||||
return a[1] > b[1]
|
||||
end)
|
||||
end
|
||||
|
||||
trace(action_tuples)
|
||||
require('guihua.gui').select(action_tuples, opts, on_user_choice)
|
||||
end
|
||||
|
||||
@ -162,8 +166,6 @@ code_action.code_action = function()
|
||||
local original_select = vim.ui.select
|
||||
vim.ui.select = sort_select
|
||||
|
||||
log('codeaction')
|
||||
|
||||
vim.lsp.buf.code_action()
|
||||
vim.defer_fn(function()
|
||||
vim.ui.select = original_select
|
||||
@ -186,17 +188,19 @@ code_action.range_code_action = function(startpos, endpos)
|
||||
|
||||
local original_input = vim.ui.input
|
||||
vim.ui.input = require('guihua.input').input
|
||||
vim.lsp.buf.range_code_action(context, startpos, endpos)
|
||||
|
||||
if vim.fn.has('nvim-0.8') then
|
||||
vim.lsp.buf.code_action({context=context ,range={start = startpos, ['end'] = endpos}})
|
||||
else
|
||||
vim.lsp.buf.range_code_action(context, startpos, endpos)
|
||||
end
|
||||
vim.defer_fn(function()
|
||||
vim.ui.select = original_select
|
||||
end, 1000)
|
||||
|
||||
vim.defer_fn(function()
|
||||
vim.ui.input = original_input
|
||||
end, 1000)
|
||||
end
|
||||
|
||||
code_action.code_action_prompt = function()
|
||||
code_action.code_action_prompt = function(bufnr)
|
||||
if special_buffers[vim.bo.filetype] then
|
||||
log('skip buffer', vim.bo.filetype)
|
||||
return
|
||||
|
@ -5,7 +5,7 @@ local codelens = require('vim.lsp.codelens')
|
||||
|
||||
local log = require('navigator.util').log
|
||||
local trace = require('navigator.util').trace
|
||||
|
||||
-- trace = log
|
||||
local lsphelper = require('navigator.lspwrapper')
|
||||
local api = vim.api
|
||||
local M = {}
|
||||
@ -61,24 +61,19 @@ local codelens_hdlr = function(err, result, ctx, cfg)
|
||||
end
|
||||
end
|
||||
|
||||
function M.setup()
|
||||
vim.cmd('highlight! link LspCodeLens LspDiagnosticsHint')
|
||||
vim.cmd('highlight! link LspCodeLensText LspDiagnosticsInformation')
|
||||
vim.cmd('highlight! link LspCodeLensTextSign LspDiagnosticsSignInformation')
|
||||
vim.cmd('highlight! link LspCodeLensTextSeparator Boolean')
|
||||
|
||||
vim.cmd('augroup navigator.codelenses')
|
||||
vim.cmd(' autocmd!')
|
||||
vim.cmd("autocmd BufEnter,CursorHold,InsertLeave <buffer> lua require('navigator.codelens').refresh()")
|
||||
vim.cmd('augroup end')
|
||||
local on_codelens = vim.lsp.handlers['textDocument/codeLens']
|
||||
vim.lsp.handlers['textDocument/codeLens'] = function(err, result, ctx, cfg)
|
||||
-- trace(err, result, ctx.client_id, ctx.bufnr, cfg or {})
|
||||
cfg = cfg or {}
|
||||
ctx = ctx or { bufnr = vim.api.nvim_get_current_buf() }
|
||||
on_codelens(err, result, ctx, cfg)
|
||||
codelens_hdlr(err, result, ctx, cfg)
|
||||
end
|
||||
function M.setup(bufnr)
|
||||
log('setup for ****** ', bufnr)
|
||||
vim.api.nvim_set_hl(0, 'LspCodeLens', { link = 'DiagnosticsHint', default = true })
|
||||
vim.api.nvim_set_hl(0, 'LspCodeLensText', { link = 'DiagnosticsInformation', default = true })
|
||||
vim.api.nvim_set_hl(0, 'LspCodeLensSign', { link = 'DiagnosticsInformation', default = true })
|
||||
vim.api.nvim_set_hl(0, 'LspCodeLensSeparator', { link = 'Boolean', default = true })
|
||||
vim.api.nvim_create_autocmd({ 'CursorHold', 'CursorHoldI', 'InsertLeave' }, {
|
||||
group = vim.api.nvim_create_augroup('nv__codelenses', {}),
|
||||
buffer = bufnr or vim.api.nvim_win_get_buf(),
|
||||
callback = function()
|
||||
require('navigator.codelens').refresh()
|
||||
end,
|
||||
})
|
||||
end
|
||||
|
||||
M.lsp_clients = {}
|
||||
@ -91,7 +86,7 @@ function M.refresh()
|
||||
if not lsphelper.check_capabilities('codeLensProvider') then
|
||||
return
|
||||
end
|
||||
vim.lsp.codelens.refresh()
|
||||
M.inline()
|
||||
end
|
||||
|
||||
local virtual_types_ns = api.nvim_create_namespace('ng_virtual_types')
|
||||
@ -106,12 +101,13 @@ function M.run_action()
|
||||
local original_select = vim.ui.select
|
||||
vim.ui.select = require('guihua.gui').select
|
||||
|
||||
log('codeaction')
|
||||
log('codelens action')
|
||||
|
||||
codelens.run()
|
||||
vim.defer_fn(function()
|
||||
vim.ui.select = original_select
|
||||
end, 1000)
|
||||
|
||||
end
|
||||
|
||||
M.inline = function()
|
||||
@ -129,42 +125,20 @@ M.inline = function()
|
||||
|
||||
local bufnr = api.nvim_get_current_buf()
|
||||
local parameter = lsp.util.make_position_params()
|
||||
local response = lsp.buf_request_sync(bufnr, 'textDocument/codeLens', parameter)
|
||||
|
||||
-- Clear previous highlighting
|
||||
api.nvim_buf_clear_namespace(bufnr, virtual_types_ns, 0, -1)
|
||||
local on_codelens = vim.lsp.handlers['textDocument/codeLens']
|
||||
lsp.buf_request(bufnr, 'textDocument/codeLens', parameter, function(err, response, ctx, _)
|
||||
-- Clear previous highlighting
|
||||
api.nvim_buf_clear_namespace(bufnr, virtual_types_ns, 0, -1)
|
||||
|
||||
if response then
|
||||
log(response)
|
||||
for _, v in ipairs(response) do
|
||||
if v == nil or v.result == nil then
|
||||
return
|
||||
end -- no response
|
||||
for _, vv in pairs(v.result) do
|
||||
local start_line = -1
|
||||
for _, vvv in pairs(vv.range) do
|
||||
start_line = tonumber(vvv.line)
|
||||
end
|
||||
if response then
|
||||
trace(response)
|
||||
|
||||
local cmd = vv.command
|
||||
local msg = _NgConfigValues.icons.code_action_icon .. ' '
|
||||
if cmd then
|
||||
local txt = cmd.title or ''
|
||||
txt = txt .. ' ' .. (cmd.command or '') .. ' '
|
||||
msg = msg .. txt .. ' '
|
||||
end
|
||||
on_codelens(err, response, ctx, _)
|
||||
|
||||
log(msg)
|
||||
api.nvim_buf_set_extmark(bufnr, virtual_types_ns, start_line, -1, {
|
||||
virt_text = { { msg, 'LspCodeLensText' } },
|
||||
virt_text_pos = 'overlay',
|
||||
hl_mode = 'combine',
|
||||
})
|
||||
end
|
||||
codelens_hdlr (err, response, ctx, _)
|
||||
end
|
||||
-- else
|
||||
-- api.nvim_command("echohl WarningMsg | echo 'VirtualTypes: No response' | echohl None")
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
return M
|
||||
|
@ -89,7 +89,7 @@ local function ctags_symbols()
|
||||
local height = _NgConfigValues.height or 0.4
|
||||
local width = _NgConfigValues.width or 0.7
|
||||
height = math.floor(height * vfn.winheight('%'))
|
||||
width = math.floor(width * vfn.winwidth('%'))
|
||||
width = math.floor(vim.api.nvim_get_option('columns') * width)
|
||||
local items = {}
|
||||
local ctags_file = _NgConfigValues.ctags.tagfile
|
||||
if not util.file_exists(ctags_file) then
|
||||
@ -118,7 +118,7 @@ local function ctags_symbols()
|
||||
local opt = {
|
||||
api = ' ',
|
||||
ft = ft,
|
||||
bg = 'GHListDark',
|
||||
bg = 'GuihuaListDark',
|
||||
data = result,
|
||||
items = result,
|
||||
enter = true,
|
||||
|
@ -74,7 +74,7 @@ local function def_preview(timeout_ms)
|
||||
local row = range.start.line
|
||||
-- in case there are comments
|
||||
row = math.max(row - 3, 1)
|
||||
local delta = range.start.line - row + 1
|
||||
local delta = range.start.line - row + 3
|
||||
local uri = data[1].uri or data[1].targetUri
|
||||
if not uri then
|
||||
return
|
||||
@ -85,7 +85,12 @@ local function def_preview(timeout_ms)
|
||||
end
|
||||
|
||||
local ok, parsers = pcall(require, 'nvim-treesitter.parsers')
|
||||
local lines_num = 12
|
||||
|
||||
-- TODO: 32/64 should be an option
|
||||
local lines_num = 64
|
||||
if range['end'] ~= nil then
|
||||
lines_num = math.max(lines_num, range['end'].line - range.start.line + 4)
|
||||
end
|
||||
if ok then
|
||||
local ts = require('navigator.treesitter')
|
||||
local root = parsers.get_parser(bufnr)
|
||||
@ -97,10 +102,10 @@ local function def_preview(timeout_ms)
|
||||
|
||||
local sr, _, er, _ = ts.get_node_scope(def_node)
|
||||
log(sr, er)
|
||||
lines_num = math.max(lines_num, er - sr + 3) -- comments etc
|
||||
lines_num = math.max(lines_num, er - sr + 5) -- comments etc
|
||||
end
|
||||
|
||||
-- TODO: 12 should be an option
|
||||
-- TODO: 32 should be an option
|
||||
local definition = vim.api.nvim_buf_get_lines(bufnr, row, range['end'].line + lines_num, false)
|
||||
local def_line = vim.api.nvim_buf_get_lines(bufnr, range.start.line, range.start.line + 1, false)
|
||||
for _ = 1, math.min(3, #definition), 1 do
|
||||
@ -112,7 +117,8 @@ local function def_preview(timeout_ms)
|
||||
end
|
||||
end
|
||||
local width = 40
|
||||
local maxwidth = math.floor(vim.fn.winwidth(0) * 4 / 5)
|
||||
|
||||
local maxwidth = math.floor( vim.api.nvim_get_option('columns') * 0.8)
|
||||
for _, value in pairs(definition) do
|
||||
-- log(key, value, width)
|
||||
width = math.max(width, #value + 4)
|
||||
@ -126,7 +132,7 @@ local function def_preview(timeout_ms)
|
||||
relative = 'cursor',
|
||||
style = 'minimal',
|
||||
ft = filetype,
|
||||
rect = { width = width, height = #definition + 3, pos_y = 2 },
|
||||
rect = { width = width, height = math.min(#definition + 3, 16), pos_y = 2 }, -- TODO: 16 hardcoded
|
||||
data = definition,
|
||||
enter = true,
|
||||
border = _NgConfigValues.border or 'shadow',
|
||||
|
@ -2,7 +2,6 @@ local gui = require('navigator.gui')
|
||||
local diagnostic_list = {}
|
||||
local diagnostic = vim.diagnostic or vim.lsp.diagnostic
|
||||
-- local hide = diagnostic.hide or diagnostic.clear
|
||||
_NG_VT_DIAG_NS = vim.api.nvim_create_namespace('navigator_lua_diag')
|
||||
local util = require('navigator.util')
|
||||
local log = util.log
|
||||
local trace = require('guihua.log').trace
|
||||
@ -11,6 +10,8 @@ local error = util.error
|
||||
local path_sep = require('navigator.util').path_sep()
|
||||
local path_cur = require('navigator.util').path_cur()
|
||||
local empty = util.empty
|
||||
local api = vim.api
|
||||
_NG_VT_DIAG_NS = api.nvim_create_namespace('navigator_lua_diag')
|
||||
|
||||
if not util.nvim_0_6_1() then
|
||||
util.warn('Navigator 0.4+ only support nvim-0.6+, please use Navigator 0.3.x or a newer version of neovim')
|
||||
@ -57,15 +58,18 @@ local function error_marker(result, ctx, config)
|
||||
if bufnr == nil then
|
||||
bufnr = vim.uri_to_bufnr(result.uri)
|
||||
end
|
||||
local fname = vim.api.nvim_buf_get_name(bufnr)
|
||||
local success, fname = pcall(api.nvim_buf_get_name, bufnr)
|
||||
if not success then
|
||||
return
|
||||
end
|
||||
local uri = vim.uri_from_fname(fname)
|
||||
if uri ~= result.uri then
|
||||
log('not same buf', ctx, result.uri, bufnr, vim.fn.bufnr())
|
||||
return
|
||||
end
|
||||
|
||||
if not vim.api.nvim_buf_is_loaded(bufnr) then
|
||||
log('buf not loaded', bufnr)
|
||||
if not api.nvim_buf_is_loaded(bufnr) then
|
||||
trace('buf not loaded', bufnr)
|
||||
return
|
||||
end
|
||||
|
||||
@ -76,7 +80,7 @@ local function error_marker(result, ctx, config)
|
||||
local diag_cnt = get_count(bufnr, [[Error]]) + get_count(bufnr, [[Warning]])
|
||||
if diag_cnt == 0 and _NG_VT_DIAG_NS ~= nil then
|
||||
log('great no errors')
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
end
|
||||
return
|
||||
end
|
||||
@ -84,12 +88,12 @@ local function error_marker(result, ctx, config)
|
||||
-- total line num of current buffer
|
||||
|
||||
-- local winid = vim.fn.win_getid(vim.fn.winnr())
|
||||
-- local winid = vim.api.nvim_get_current_win()
|
||||
local total_num = vim.api.nvim_buf_line_count(bufnr)
|
||||
-- local winid = api.nvim_get_current_win()
|
||||
local total_num = api.nvim_buf_line_count(bufnr)
|
||||
-- local total_num = vim.fn.getbufinfo(vim.fn.winbufnr(winid))[1].linecount
|
||||
-- window size of current buffer
|
||||
|
||||
local stats = vim.api.nvim_list_uis()[1]
|
||||
local stats = api.nvim_list_uis()[1]
|
||||
-- local wwidth = stats.width;
|
||||
local wheight = stats.height
|
||||
|
||||
@ -97,7 +101,7 @@ local function error_marker(result, ctx, config)
|
||||
return
|
||||
end
|
||||
if _NG_VT_DIAG_NS == nil then
|
||||
_NG_VT_DIAG_NS = vim.api.nvim_create_namespace('navigator_lua_diag')
|
||||
_NG_VT_DIAG_NS = api.nvim_create_namespace('navigator_lua_diag')
|
||||
end
|
||||
|
||||
local pos = {}
|
||||
@ -139,7 +143,7 @@ local function error_marker(result, ctx, config)
|
||||
end
|
||||
|
||||
if not vim.tbl_isempty(pos) then
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
end
|
||||
for _, s in pairs(pos) do
|
||||
local hl = 'ErrorMsg'
|
||||
@ -160,7 +164,7 @@ local function error_marker(result, ctx, config)
|
||||
end
|
||||
trace('add pos', s, bufnr)
|
||||
|
||||
vim.api.nvim_buf_set_extmark(
|
||||
api.nvim_buf_set_extmark(
|
||||
bufnr,
|
||||
_NG_VT_DIAG_NS,
|
||||
l,
|
||||
@ -184,9 +188,9 @@ local diag_hdlr = function(err, result, ctx, config)
|
||||
return
|
||||
end
|
||||
|
||||
local mode = vim.api.nvim_get_mode().mode
|
||||
local mode = api.nvim_get_mode().mode
|
||||
if mode ~= 'n' and config.update_in_insert == false then
|
||||
log('skip sign update in insert mode')
|
||||
trace('skip sign update in insert mode')
|
||||
end
|
||||
local cwd = vim.loop.cwd()
|
||||
local ft = vim.bo.filetype
|
||||
@ -222,14 +226,18 @@ local diag_hdlr = function(err, result, ctx, config)
|
||||
item.uri = uri
|
||||
-- trace(item)
|
||||
local head = _NgConfigValues.icons.diagnostic_head
|
||||
if v.severity == 1 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_1
|
||||
end
|
||||
if v.severity == 2 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_2
|
||||
end
|
||||
if v.severity > 2 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_3
|
||||
if v.severity then
|
||||
if v.severity == 1 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_1
|
||||
end
|
||||
if v.severity == 2 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_2
|
||||
end
|
||||
if v.severity > 2 then
|
||||
head = _NgConfigValues.icons.diagnostic_head_severity_3
|
||||
end
|
||||
else
|
||||
v.severity = 2
|
||||
end
|
||||
if v.relatedInformation and v.relatedInformation[1] then
|
||||
local info = v.relatedInformation[1]
|
||||
@ -242,7 +250,7 @@ local diag_hdlr = function(err, result, ctx, config)
|
||||
end
|
||||
end
|
||||
local bufnr1 = vim.uri_to_bufnr(uri)
|
||||
local loaded = vim.api.nvim_buf_is_loaded(bufnr1)
|
||||
local loaded = api.nvim_buf_is_loaded(bufnr1)
|
||||
if _NgConfigValues.diagnostic_load_files then
|
||||
-- print('load buffers')
|
||||
if not loaded then
|
||||
@ -250,7 +258,7 @@ local diag_hdlr = function(err, result, ctx, config)
|
||||
end
|
||||
local pos = v.range.start
|
||||
local row = pos.line
|
||||
local line = (vim.api.nvim_buf_get_lines(bufnr1, row, row + 1, false) or { '' })[1]
|
||||
local line = (api.nvim_buf_get_lines(bufnr1, row, row + 1, false) or { '' })[1]
|
||||
if line ~= nil then
|
||||
item.text = head .. line .. _NgConfigValues.icons.diagnostic_head_description .. v.message
|
||||
else
|
||||
@ -284,7 +292,7 @@ local diag_hdlr = function(err, result, ctx, config)
|
||||
marker(result, ctx, config)
|
||||
else
|
||||
trace('great, no diag errors')
|
||||
vim.api.nvim_buf_clear_namespace(0, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(0, _NG_VT_DIAG_NS, 0, -1)
|
||||
_NG_VT_DIAG_NS = nil
|
||||
end
|
||||
end
|
||||
@ -327,18 +335,24 @@ function M.setup()
|
||||
vim.diagnostic.config(diagnostic_cfg)
|
||||
|
||||
if _NgConfigValues.lsp.diagnostic_scrollbar_sign then
|
||||
vim.cmd([[autocmd WinScrolled * lua require'navigator.diagnostics'.update_err_marker()]])
|
||||
api.nvim_create_autocmd({ 'WinScrolled' }, {
|
||||
group = api.nvim_create_augroup('NGWinScrolledGroup', {}),
|
||||
pattern = '*',
|
||||
callback = function()
|
||||
require('navigator.diagnostics').update_err_marker()
|
||||
end,
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
local function clear_diag_VT(bufnr) -- important for clearing out when no more errors
|
||||
bufnr = bufnr or vim.api.nvim_get_current_buf()
|
||||
bufnr = bufnr or api.nvim_get_current_buf()
|
||||
log(bufnr, _NG_VT_DIAG_NS)
|
||||
if _NG_VT_DIAG_NS == nil then
|
||||
return
|
||||
end
|
||||
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
_NG_VT_DIAG_NS = nil
|
||||
end
|
||||
|
||||
@ -380,15 +394,15 @@ M.show_buf_diagnostics = function()
|
||||
end
|
||||
trace('new buffer', listview.bufnr)
|
||||
if listview.bufnr then
|
||||
vim.api.nvim_buf_add_highlight(listview.bufnr, -1, 'Title', 0, 0, -1)
|
||||
api.nvim_buf_add_highlight(listview.bufnr, -1, 'Title', 0, 0, -1)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- set loc list win
|
||||
M.set_diag_loclist = function()
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
M.set_diag_loclist = function(bufnr)
|
||||
bufnr = bufnr or api.nvim_get_current_buf()
|
||||
local diag_cnt = get_count(bufnr, [[Error]]) + get_count(bufnr, [[Warning]])
|
||||
if diag_cnt == 0 then
|
||||
log('great, no errors!')
|
||||
@ -408,7 +422,7 @@ M.set_diag_loclist = function()
|
||||
if diagnostic.set_loclist then
|
||||
diagnostic.set_loclist(cfg)
|
||||
else
|
||||
cfg.namespaces = diagnostic.get_namespace(nil)
|
||||
cfg.namespaces = diagnostic.get_namespaces()
|
||||
diagnostic.setloclist(cfg)
|
||||
end
|
||||
else
|
||||
@ -424,7 +438,7 @@ function M.update_err_marker()
|
||||
-- nothing to update
|
||||
return
|
||||
end
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local bufnr = api.nvim_get_current_buf()
|
||||
|
||||
local diag_cnt = get_count(bufnr, [[Error]])
|
||||
+ get_count(bufnr, [[Warning]])
|
||||
@ -433,12 +447,12 @@ function M.update_err_marker()
|
||||
|
||||
-- redraw
|
||||
if diag_cnt == 0 and _NG_VT_DIAG_NS ~= nil then
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
trace('no errors')
|
||||
return
|
||||
end
|
||||
|
||||
vim.api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
api.nvim_buf_clear_namespace(bufnr, _NG_VT_DIAG_NS, 0, -1)
|
||||
local errors = diagnostic.get(bufnr)
|
||||
if #errors == 0 then
|
||||
trace('no errors', errors)
|
||||
@ -453,25 +467,39 @@ function M.update_err_marker()
|
||||
end
|
||||
|
||||
function M.get_line_diagnostic()
|
||||
local lnum = vim.api.nvim_win_get_cursor(0)[1] - 1
|
||||
return diagnostic.get(vim.api.nvim_get_current_buf(), { lnum = lnum })
|
||||
local lnum = api.nvim_win_get_cursor(0)[1] - 1
|
||||
local diags = diagnostic.get(api.nvim_get_current_buf(), { lnum = lnum })
|
||||
|
||||
table.sort(diags, function(diag1, diag2)
|
||||
return diag1.severity < diag2.severity
|
||||
end)
|
||||
return diags
|
||||
end
|
||||
|
||||
function M.show_diagnostics(pos)
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local lnum = vim.api.nvim_win_get_cursor(0)[1] - 1
|
||||
local opt = { border = 'single' }
|
||||
if diagnostic.open_float and type(diagnostic.open_float) == 'function' then
|
||||
local bufnr = api.nvim_get_current_buf()
|
||||
|
||||
local lnum, col = unpack(api.nvim_win_get_cursor(0))
|
||||
lnum = lnum - 1
|
||||
local opt = { border = 'single', severity_sort = true }
|
||||
|
||||
if pos ~= nil and type(pos) == 'number' then
|
||||
opt.scope = 'buffer'
|
||||
else
|
||||
if pos == true then
|
||||
opt.scope = 'cursor'
|
||||
else
|
||||
opt.scope = 'line'
|
||||
end
|
||||
diagnostic.open_float(bufnr, opt)
|
||||
else
|
||||
-- deprecated
|
||||
diagnostic.show_line_diagnostics(opt, bufnr, lnum)
|
||||
end
|
||||
|
||||
local diags = M.get_line_diagnostic()
|
||||
if diags == nil or next(diags) == nil then
|
||||
return
|
||||
end
|
||||
local diag1 = diags[1]
|
||||
opt.offset_x = -1 * (col - diag1.col)
|
||||
diagnostic.open_float(bufnr, opt)
|
||||
end
|
||||
|
||||
function M.treesitter_and_diag_panel()
|
||||
@ -481,7 +509,7 @@ function M.treesitter_and_diag_panel()
|
||||
local results = diagnostic_list[ft]
|
||||
log(diagnostic_list, ft)
|
||||
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local bufnr = api.nvim_get_current_buf()
|
||||
local p = Panel:new({
|
||||
header = 'treesitter',
|
||||
render = function(b)
|
||||
@ -491,7 +519,8 @@ function M.treesitter_and_diag_panel()
|
||||
})
|
||||
p:add_section({
|
||||
header = 'diagnostic',
|
||||
render = function(bufnr)
|
||||
render = function(buf)
|
||||
log(buf, diagnostic)
|
||||
if diagnostic_list[ft] ~= nil then
|
||||
local display_items = {}
|
||||
for _, client_items in pairs(results) do
|
||||
|
@ -145,7 +145,6 @@ local handle_document_highlight = function(_, result, ctx)
|
||||
return
|
||||
end
|
||||
if type(result) ~= 'table' or vim.fn.empty(result) == 1 then
|
||||
log('clear up', result)
|
||||
vim.lsp.util.buf_clear_references(ctx.bufnr)
|
||||
return
|
||||
end
|
||||
@ -205,29 +204,45 @@ local function cmd_nohl()
|
||||
end
|
||||
end
|
||||
|
||||
local nav_doc_hl = function()
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local nav_doc_hl = function(bufnr)
|
||||
trace('nav_doc_hl', bufnr)
|
||||
bufnr = bufnr or vim.api.nvim_get_current_buf()
|
||||
local ref_params = vim.lsp.util.make_position_params()
|
||||
vim.lsp.for_each_buffer_client(bufnr, function(client, _, _)
|
||||
if client.server_capabilities.documentHighlightProvider == true then
|
||||
trace('sending doc highlight', client.name, bufnr)
|
||||
client.request('textDocument/documentHighlight', ref_params, handle_document_highlight, bufnr)
|
||||
end
|
||||
end)
|
||||
end
|
||||
|
||||
local function documentHighlight()
|
||||
api.nvim_exec(
|
||||
[[
|
||||
augroup lsp_document_highlight
|
||||
autocmd! * <buffer>
|
||||
autocmd CursorHold,CursorHoldI <buffer> lua require('navigator.dochighlight').nav_doc_hl()
|
||||
autocmd CursorMoved <buffer> lua vim.lsp.buf.clear_references()
|
||||
augroup END
|
||||
]],
|
||||
false
|
||||
)
|
||||
local function documentHighlight(bufnr)
|
||||
bufnr = bufnr or api.nvim_get_current_buf()
|
||||
|
||||
if _NgConfigValues.lsp.document_highlight == true then
|
||||
local group_name = string.format('%s%d', 'NGHiGroup', bufnr)
|
||||
local cmd_group = api.nvim_create_augroup(group_name, {})
|
||||
api.nvim_create_autocmd({ 'CursorHold', 'CursorHoldI' }, {
|
||||
group = cmd_group,
|
||||
buffer = bufnr,
|
||||
desc = 'document highlight',
|
||||
callback = function()
|
||||
require('navigator.dochighlight').nav_doc_hl(bufnr)
|
||||
end,
|
||||
})
|
||||
|
||||
api.nvim_create_autocmd({ 'CursorMoved', 'CursorMovedI' }, {
|
||||
group = cmd_group,
|
||||
buffer = bufnr,
|
||||
desc = 'clear document highlight',
|
||||
callback = function()
|
||||
vim.lsp.util.buf_clear_references(bufnr)
|
||||
end,
|
||||
})
|
||||
end
|
||||
|
||||
vim.lsp.handlers['textDocument/documentHighlight'] = function(err, result, ctx)
|
||||
local bufnr = ctx.bufnr or api.nvim_get_current_buf()
|
||||
local buffer = ctx.bufnr or api.nvim_get_current_buf()
|
||||
if err then
|
||||
vim.notify(err, vim.lsp.log_levels.ERROR)
|
||||
return
|
||||
@ -236,19 +251,18 @@ local function documentHighlight()
|
||||
return
|
||||
end
|
||||
trace('dochl', result)
|
||||
bufnr = bufnr or 0
|
||||
if type(result) ~= 'table' then
|
||||
vim.lsp.util.buf_clear_references(bufnr)
|
||||
vim.lsp.util.buf_clear_references(buffer)
|
||||
return
|
||||
end
|
||||
local client_id = ctx.client_id
|
||||
vim.lsp.util.buf_clear_references(bufnr)
|
||||
vim.lsp.util.buf_highlight_references(bufnr, result, util.encoding(client_id))
|
||||
vim.lsp.util.buf_clear_references(buffer)
|
||||
vim.lsp.util.buf_highlight_references(buffer, result, util.encoding(client_id))
|
||||
table.sort(result, function(a, b)
|
||||
return before(a.range, b.range)
|
||||
end)
|
||||
references[bufnr] = result
|
||||
add_locs(bufnr, result)
|
||||
references[buffer] = result
|
||||
add_locs(buffer, result)
|
||||
end
|
||||
end
|
||||
|
||||
|
@ -28,19 +28,14 @@ function M.on_attach()
|
||||
end
|
||||
|
||||
function M.setup_plugin()
|
||||
api.nvim_command('augroup FoldingCommand')
|
||||
api.nvim_command('autocmd! * <buffer>')
|
||||
api.nvim_command("autocmd BufEnter <buffer> lua require'navigator.foldlsp'.update_folds()")
|
||||
api.nvim_command("autocmd BufWritePost <buffer> lua require'navigator.foldlsp'.update_folds()")
|
||||
api.nvim_command('augroup end')
|
||||
|
||||
-- vim.cmd([[
|
||||
--
|
||||
-- function! folding_nvim#foldexpr()
|
||||
-- return luaeval(printf('require"navigator.foldlsp".get_fold_indic(%d)', v:lnum))
|
||||
-- endfunction
|
||||
--
|
||||
-- ]])
|
||||
local cmd_group = api.nvim_create_augroup('NGFoldGroup', {})
|
||||
api.nvim_create_autocmd({ 'BufEnter', 'BufWritePost' }, {
|
||||
group = cmd_group,
|
||||
pattern = '*',
|
||||
callback = function()
|
||||
require('navigator.foldlsp').update_folds()
|
||||
end,
|
||||
})
|
||||
|
||||
local clients = vim.lsp.buf_get_clients(0)
|
||||
|
||||
|
@ -21,7 +21,12 @@ function NG_custom_fold_text()
|
||||
local line = vim.fn.getline(vim.v.foldstart)
|
||||
local line_count = vim.v.foldend - vim.v.foldstart + 1
|
||||
-- log("" .. line .. " // " .. line_count .. " lines")
|
||||
return ' ⚡' .. line .. ': ' .. line_count .. ' lines'
|
||||
local ss, se = line:find('^%s*')
|
||||
local spaces = line:sub(ss, se)
|
||||
local tabspace = string.rep(' ', vim.o.tabstop)
|
||||
spaces = spaces:gsub('\t', tabspace)
|
||||
line = line:gsub('^%s*(.-)%s*$', '%1')
|
||||
return spaces .. '⚡' .. line .. ': ' .. line_count .. ' lines'
|
||||
end
|
||||
|
||||
vim.opt.foldtext = NG_custom_fold_text()
|
||||
@ -220,7 +225,7 @@ function M.get_fold_indic(lnum)
|
||||
local buf = api.nvim_get_current_buf()
|
||||
local shown = false
|
||||
for i = 1, vim.fn.tabpagenr('$') do
|
||||
for key, value in pairs(vim.fn.tabpagebuflist(i)) do
|
||||
for _, value in pairs(vim.fn.tabpagebuflist(i)) do
|
||||
if value == buf then
|
||||
shown = true
|
||||
end
|
||||
|
@ -1,5 +1,6 @@
|
||||
-- https://github.com/wention/dotfiles/blob/master/.config/nvim/lua/config/lsp.lua
|
||||
-- https://github.com/lukas-reineke/dotfiles/blob/master/vim/lua/lsp/handlers.lua
|
||||
|
||||
return {
|
||||
format_hdl = function(err, result, ctx, _) -- FIXME: bufnr is nil
|
||||
if err ~= nil or result == nil then
|
||||
@ -31,11 +32,13 @@ return {
|
||||
end
|
||||
end, 100)
|
||||
end,
|
||||
range_foramt = function(err, result, ctx, _)
|
||||
range_format = function()
|
||||
local old_func = vim.go.operatorfunc
|
||||
_G.op_func_formatting = function()
|
||||
print('formatting range')
|
||||
local start = vim.api.nvim_buf_get_mark(0, '[')
|
||||
local finish = vim.api.nvim_buf_get_mark(0, ']')
|
||||
print(vim.inspect(start), vim.inspect(finish))
|
||||
vim.lsp.buf.range_formatting({}, start, finish)
|
||||
vim.go.operatorfunc = old_func
|
||||
_G.op_func_formatting = nil
|
||||
|
@ -1,6 +1,6 @@
|
||||
local M = {}
|
||||
local ListView = require('guihua.listview')
|
||||
local TextView = require('guihua.textview')
|
||||
-- local ListView = require('guihua.listview')
|
||||
-- local TextView = require('guihua.textview')
|
||||
local util = require('navigator.util')
|
||||
local log = util.log
|
||||
local trace = require('navigator.util').trace
|
||||
@ -16,7 +16,7 @@ function M.new_list_view(opts)
|
||||
local winnr = active_list_view.win
|
||||
local bufnr = active_list_view.buf
|
||||
|
||||
if bufnr and vim.api.nvim_buf_is_valid(bufnr) and winnr and vim.api.nvim_win_is_valid(winnr) then
|
||||
if bufnr and api.nvim_buf_is_valid(bufnr) and winnr and api.nvim_win_is_valid(winnr) then
|
||||
log('list view already present')
|
||||
return active_list_view
|
||||
end
|
||||
@ -35,6 +35,14 @@ function M.new_list_view(opts)
|
||||
opts.border = config.border or 'shadow'
|
||||
if vim.fn.hlID('TelescopePromptBorder') > 0 then
|
||||
opts.border_hl = 'TelescopePromptBorder'
|
||||
opts.list_hl = 'TelescopeNormal'
|
||||
opts.bg_hl = 'TelescopePreviewNormal'
|
||||
opts.sel_hl = 'TelescopeSelection'
|
||||
else
|
||||
opts.border_hl = 'FloatBorder'
|
||||
opts.bg_hl = 'NormalFloat'
|
||||
opts.list_hl = 'NormalFloat'
|
||||
opts.sel_hl = 'PmenuSel'
|
||||
end
|
||||
if not items or vim.tbl_isempty(items) then
|
||||
log('empty data return')
|
||||
|
@ -100,7 +100,7 @@ hierarchy_handler = function(dir, handler, show, api, err, result, ctx, cfg)
|
||||
trace(dir, handler, api, show, err, result, ctx, cfg)
|
||||
ctx = ctx or {} -- can be nil if it is async call
|
||||
cfg = cfg or {}
|
||||
opts = ctx.opts or {}
|
||||
local opts = ctx.opts or {}
|
||||
vim.validate({ handler = { handler, 'function' }, show = { show, 'function' }, api = { api, 'string' } })
|
||||
local bufnr = ctx.bufnr or vim.api.nvim_get_current_buf()
|
||||
assert(next(vim.lsp.buf_get_clients(bufnr)), 'Must have a client running to use lsp hierarchy')
|
||||
@ -142,11 +142,12 @@ local function display_panel(args)
|
||||
|
||||
local Panel = require('guihua.panel')
|
||||
local bufnr = args.bufnr or vim.api.nvim_get_current_buf()
|
||||
local ft = args.ft or vim.api.nvim_buf_get_option(bufnr, 'buftype')
|
||||
-- local ft = args.ft or vim.api.nvim_buf_get_option(bufnr, 'buftype')
|
||||
local items = args.items
|
||||
local p = Panel:new({
|
||||
header = args.header or 'Call Hierarchy',
|
||||
render = function(bufnr)
|
||||
render = function(buf)
|
||||
log(buf)
|
||||
return items
|
||||
end,
|
||||
fold = function(panel, node)
|
||||
|
@ -1,7 +1,6 @@
|
||||
return {
|
||||
init = function()
|
||||
local loader = nil
|
||||
local packer_plugins = packer_plugins or nil -- suppress warnings
|
||||
local log = require('navigator.util').log
|
||||
-- packer only
|
||||
if packer_plugins ~= nil then -- packer install
|
||||
@ -51,7 +50,7 @@ return {
|
||||
end,
|
||||
load = function(plugin_name, path)
|
||||
local loader = nil
|
||||
local packer_plugins = packer_plugins or nil -- suppress warnings
|
||||
packer_plugins = packer_plugins or nil -- suppress warnings
|
||||
-- packer only
|
||||
if packer_plugins ~= nil then -- packer install
|
||||
local lazy_plugins = {}
|
||||
|
@ -4,7 +4,7 @@ local lsp = require('vim.lsp')
|
||||
local util = require('navigator.util')
|
||||
local log = util.log
|
||||
local trace = util.trace
|
||||
|
||||
_NG_Attached = {}
|
||||
local M = {}
|
||||
|
||||
M.on_attach = function(client, bufnr)
|
||||
@ -23,6 +23,7 @@ M.on_attach = function(client, bufnr)
|
||||
log('attaching: ', bufnr, client.name, uri)
|
||||
|
||||
trace(client)
|
||||
_NG_Attached[client.name] = true
|
||||
|
||||
-- add highlight for Lspxxx
|
||||
require('navigator.lspclient.highlight').add_highlight()
|
||||
@ -35,9 +36,16 @@ M.on_attach = function(client, bufnr)
|
||||
})
|
||||
|
||||
if client.server_capabilities.documentHighlightProvider == true then
|
||||
require('navigator.dochighlight').documentHighlight()
|
||||
trace('attaching doc highlight: ', bufnr, client.name)
|
||||
vim.defer_fn(function()
|
||||
require('navigator.dochighlight').documentHighlight(bufnr)
|
||||
end, 50) -- allow a bit time for it to settle down
|
||||
else
|
||||
log('skip doc highlight: ', bufnr, client.name)
|
||||
end
|
||||
|
||||
|
||||
|
||||
require('navigator.lspclient.lspkind').init()
|
||||
|
||||
local config = require('navigator').config_values()
|
||||
@ -62,9 +70,13 @@ M.on_attach = function(client, bufnr)
|
||||
if _NgConfigValues.lsp.code_action.enable then
|
||||
if client.server_capabilities.codeActionProvider and client.name ~= 'null-ls' then
|
||||
log('code action enabled for client', client.server_capabilities.codeActionProvider)
|
||||
api.nvim_command('augroup NCodeAction')
|
||||
vim.cmd([[autocmd CursorHold,CursorHoldI <buffer> lua require'navigator.codeAction'.code_action_prompt()]])
|
||||
api.nvim_command('augroup end')
|
||||
api.nvim_create_autocmd({ 'CursorHold', 'CursorHoldI' }, {
|
||||
group = api.nvim_create_augroup('NGCodeActGroup_'..tostring(bufnr), {}),
|
||||
buffer = bufnr,
|
||||
callback = function()
|
||||
require('navigator.codeAction').code_action_prompt(bufnr)
|
||||
end,
|
||||
})
|
||||
end
|
||||
end
|
||||
end
|
||||
|
@ -4,6 +4,7 @@ local log = ng_util.log
|
||||
local trace = ng_util.trace
|
||||
local empty = ng_util.empty
|
||||
local warn = ng_util.warn
|
||||
local vfn = vim.fn
|
||||
_NG_Loaded = {}
|
||||
|
||||
_LoadedFiletypes = {}
|
||||
@ -41,6 +42,7 @@ local disabled_ft = {
|
||||
'windline',
|
||||
'notify',
|
||||
'nofile',
|
||||
'help',
|
||||
'',
|
||||
}
|
||||
-- local cap = vim.lsp.protocol.make_client_capabilities()
|
||||
@ -65,324 +67,43 @@ local luadevcfg = {
|
||||
local luadev = {}
|
||||
local user_luadev = _NgConfigValues.lsp['lua-dev']
|
||||
if user_luadev then
|
||||
luadev = vim.tbl_deep_extend('force', luadev, user_luadev)
|
||||
luadev = vim.tbl_deep_extend('force', luadev, user_luadev)
|
||||
end
|
||||
require('navigator.lazyloader').load('lua-dev.nvim', 'folke/lua-dev.nvim')
|
||||
if _NgConfigValues.lsp_installer then
|
||||
require('navigator.lazyloader').load('nvim-lsp-installer', 'williamboman/nvim-lsp-installer')
|
||||
end
|
||||
local ok, l = pcall(require, 'lua-dev')
|
||||
if ok and l then
|
||||
luadev = l.setup(luadevcfg)
|
||||
|
||||
|
||||
if _NgConfigValues.mason then
|
||||
require('navigator.lazyloader').load('mason.nvim', 'williamboman/mason.nvim')
|
||||
require('navigator.lazyloader').load('mason-lspconfig.nvim', 'williamboman/mason-lspconfig.nvim')
|
||||
end
|
||||
|
||||
local function add(lib)
|
||||
for _, p in pairs(vim.fn.expand(lib, false, true)) do
|
||||
p = vim.loop.fs_realpath(p)
|
||||
if p then
|
||||
library[p] = true
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
-- add runtime
|
||||
add('$VIMRUNTIME')
|
||||
|
||||
-- add your config
|
||||
-- local home = vim.fn.expand("$HOME")
|
||||
add(vim.fn.stdpath('config'))
|
||||
|
||||
-- add plugins it may be very slow to add all in path
|
||||
-- if vim.fn.isdirectory(home .. "/.config/share/nvim/site/pack/packer") then
|
||||
-- add(home .. "/.local/share/nvim/site/pack/packer/opt/*")
|
||||
-- add(home .. "/.local/share/nvim/site/pack/packer/start/*")
|
||||
-- end
|
||||
|
||||
library[vim.fn.expand('$VIMRUNTIME/lua')] = true
|
||||
library[vim.fn.expand('$VIMRUNTIME/lua/vim')] = true
|
||||
library[vim.fn.expand('$VIMRUNTIME/lua/vim/lsp')] = true
|
||||
-- [vim.fn.expand("~/repos/nvim/lua")] = true
|
||||
|
||||
-- TODO remove onece PR #944 merged to lspconfig
|
||||
local path_sep = require('navigator.util').path_sep()
|
||||
local strip_dir_pat = path_sep .. '([^' .. path_sep .. ']+)$'
|
||||
local strip_sep_pat = path_sep .. '$'
|
||||
local dirname = function(pathname)
|
||||
if not pathname or #pathname == 0 then
|
||||
return
|
||||
end
|
||||
local result = pathname:gsub(strip_sep_pat, ''):gsub(strip_dir_pat, '')
|
||||
if #result == 0 then
|
||||
return '/'
|
||||
end
|
||||
return result
|
||||
end
|
||||
-- TODO end
|
||||
|
||||
local setups = {
|
||||
clojure_lsp = {
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('deps.edn', 'build.boot', 'project.clj', 'shadow-cljs.edn', 'bb.edn', '.git')(fname)
|
||||
or util.path.dirname(fname)
|
||||
end,
|
||||
on_attach = on_attach,
|
||||
filetypes = { 'clojure', 'edn' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
cmd = { 'clojure-lsp' },
|
||||
},
|
||||
|
||||
elixirls = {
|
||||
on_attach = on_attach,
|
||||
filetypes = { 'elixir', 'eelixir' },
|
||||
cmd = { 'elixir-ls' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
settings = {
|
||||
elixirLS = {
|
||||
dialyzerEnabled = true,
|
||||
fetchDeps = false,
|
||||
},
|
||||
},
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('mix.exs', '.git')(fname) or util.path.dirname(fname)
|
||||
end,
|
||||
},
|
||||
|
||||
gopls = {
|
||||
on_attach = on_attach,
|
||||
-- capabilities = cap,
|
||||
filetypes = { 'go', 'gomod', 'gohtmltmpl', 'gotexttmpl' },
|
||||
message_level = vim.lsp.protocol.MessageType.Error,
|
||||
cmd = {
|
||||
'gopls', -- share the gopls instance if there is one already
|
||||
'-remote=auto', --[[ debug options ]] --
|
||||
-- "-logfile=auto",
|
||||
-- "-debug=:0",
|
||||
'-remote.debug=:0',
|
||||
-- "-rpc.trace",
|
||||
},
|
||||
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 1000 },
|
||||
settings = {
|
||||
gopls = {
|
||||
-- more settings: https://github.com/golang/tools/blob/master/gopls/doc/settings.md
|
||||
-- flags = {allow_incremental_sync = true, debounce_text_changes = 500},
|
||||
-- not supported
|
||||
analyses = { unusedparams = true, unreachable = false },
|
||||
codelenses = {
|
||||
generate = true, -- show the `go generate` lens.
|
||||
gc_details = true, -- // Show a code lens toggling the display of gc's choices.
|
||||
test = true,
|
||||
tidy = true,
|
||||
},
|
||||
usePlaceholders = true,
|
||||
completeUnimported = true,
|
||||
staticcheck = true,
|
||||
matcher = 'fuzzy',
|
||||
diagnosticsDelay = '500ms',
|
||||
experimentalWatchedFileDelay = '1000ms',
|
||||
symbolMatcher = 'fuzzy',
|
||||
gofumpt = false, -- true, -- turn on for new repos, gofmpt is good but also create code turmoils
|
||||
buildFlags = { '-tags', 'integration' },
|
||||
-- buildFlags = {"-tags", "functional"}
|
||||
},
|
||||
},
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('go.mod', '.git')(fname) or dirname(fname) -- util.path.dirname(fname)
|
||||
end,
|
||||
},
|
||||
clangd = {
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
cmd = {
|
||||
'clangd',
|
||||
'--background-index',
|
||||
'--suggest-missing-includes',
|
||||
'--clang-tidy',
|
||||
'--header-insertion=iwyu',
|
||||
'--clang-tidy-checks=-*,llvm-*,clang-analyzer-*',
|
||||
'--cross-file-rename',
|
||||
},
|
||||
filetypes = { 'c', 'cpp', 'objc', 'objcpp' },
|
||||
on_attach = function(client, bufnr)
|
||||
client.server_capabilities.documentFormattingProvider = client.server_capabilities.documentFormattingProvider
|
||||
or true
|
||||
on_attach(client, bufnr)
|
||||
end,
|
||||
},
|
||||
rust_analyzer = {
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('Cargo.toml', 'rust-project.json', '.git')(fname) or util.path.dirname(fname)
|
||||
end,
|
||||
filetypes = { 'rust' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
on_attach = on_attach,
|
||||
settings = {
|
||||
['rust-analyzer'] = {
|
||||
assist = { importMergeBehavior = 'last', importPrefix = 'by_self' },
|
||||
cargo = { loadOutDirsFromCheck = true },
|
||||
procMacro = { enable = true },
|
||||
},
|
||||
},
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
},
|
||||
sqls = {
|
||||
filetypes = { 'sql' },
|
||||
on_attach = function(client, _)
|
||||
client.server_capabilities.executeCommandProvider = client.server_capabilities.documentFormattingProvider or true
|
||||
highlight.diagnositc_config_sign()
|
||||
require('sqls').setup({ picker = 'telescope' }) -- or default
|
||||
end,
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
cmd = { 'sqls', '-config', '$HOME/.config/sqls/config.yml' },
|
||||
-- alterantively:
|
||||
-- connections = {
|
||||
-- {
|
||||
-- driver = 'postgresql',
|
||||
-- datasourcename = 'host=127.0.0.1 port=5432 user=postgres password=password dbname=user_db sslmode=disable',
|
||||
-- },
|
||||
-- },
|
||||
},
|
||||
},
|
||||
sumneko_lua = {
|
||||
cmd = { 'lua-language-server' },
|
||||
filetypes = { 'lua' },
|
||||
on_attach = on_attach,
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
Lua = {
|
||||
runtime = {
|
||||
-- Tell the language server which version of Lua you're using (most likely LuaJIT in the case of Neovim)
|
||||
version = 'LuaJIT',
|
||||
},
|
||||
diagnostics = {
|
||||
enable = true,
|
||||
-- Get the language server to recognize the `vim` global
|
||||
globals = { 'vim', 'describe', 'it', 'before_each', 'after_each', 'teardown', 'pending' },
|
||||
},
|
||||
completion = { callSnippet = 'Both' },
|
||||
workspace = {
|
||||
-- Make the server aware of Neovim runtime files
|
||||
library = library,
|
||||
maxPreload = 2000,
|
||||
preloadFileSize = 40000,
|
||||
},
|
||||
telemetry = { enable = false },
|
||||
},
|
||||
},
|
||||
on_new_config = function(cfg, root)
|
||||
local libs = vim.tbl_deep_extend('force', {}, library)
|
||||
libs[root] = nil
|
||||
cfg.settings.Lua.workspace.library = libs
|
||||
return cfg
|
||||
end,
|
||||
},
|
||||
pyright = {
|
||||
on_attach = on_attach,
|
||||
cmd = { 'pyright-langserver', '--stdio' },
|
||||
filetypes = { 'python' },
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
python = {
|
||||
formatting = { provider = 'black' },
|
||||
analysis = {
|
||||
autoSearchPaths = true,
|
||||
useLibraryCodeForTypes = true,
|
||||
diagnosticMode = 'workspace',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
ccls = {
|
||||
on_attach = on_attach,
|
||||
init_options = {
|
||||
compilationDatabaseDirectory = 'build',
|
||||
root_dir = [[ util.root_pattern("compile_commands.json", "compile_flags.txt", "CMakeLists.txt", "Makefile", ".git") or util.path.dirname ]],
|
||||
index = { threads = 2 },
|
||||
clang = { excludeArgs = { '-frounding-math' } },
|
||||
},
|
||||
flags = { allow_incremental_sync = true },
|
||||
},
|
||||
jdtls = {
|
||||
settings = {
|
||||
java = { signatureHelp = { enabled = true }, contentProvider = { preferred = 'fernflower' } },
|
||||
},
|
||||
},
|
||||
omnisharp = {
|
||||
cmd = { 'omnisharp', '--languageserver', '--hostPID', tostring(vim.fn.getpid()) },
|
||||
},
|
||||
terraformls = {
|
||||
filetypes = { 'terraform', 'tf' },
|
||||
},
|
||||
|
||||
sourcekit = {
|
||||
cmd = { 'sourcekit-lsp' },
|
||||
filetypes = { 'swift' }, -- This is recommended if you have separate settings for clangd.
|
||||
},
|
||||
}
|
||||
|
||||
setups.sumneko_lua = vim.tbl_deep_extend('force', luadev, setups.sumneko_lua)
|
||||
|
||||
local servers = {
|
||||
'angularls',
|
||||
'gopls',
|
||||
'tsserver',
|
||||
'flow',
|
||||
'bashls',
|
||||
'dockerls',
|
||||
'julials',
|
||||
'pylsp',
|
||||
'pyright',
|
||||
'jedi_language_server',
|
||||
'jdtls',
|
||||
'sumneko_lua',
|
||||
'vimls',
|
||||
'html',
|
||||
'jsonls',
|
||||
'solargraph',
|
||||
'cssls',
|
||||
'yamlls',
|
||||
'clangd',
|
||||
'ccls',
|
||||
'sqls',
|
||||
'denols',
|
||||
'graphql',
|
||||
'dartls',
|
||||
'dotls',
|
||||
'kotlin_language_server',
|
||||
'nimls',
|
||||
'intelephense',
|
||||
'vuels',
|
||||
'phpactor',
|
||||
'omnisharp',
|
||||
'r_language_server',
|
||||
'rust_analyzer',
|
||||
'terraformls',
|
||||
'svelte',
|
||||
'texlab',
|
||||
'clojure_lsp',
|
||||
'elixirls',
|
||||
'sourcekit',
|
||||
'fsautocomplete',
|
||||
'vls',
|
||||
'hls',
|
||||
'tflint',
|
||||
'terraform_lsp',
|
||||
}
|
||||
local setups = require('navigator.lspclient.clients_default').defaults()
|
||||
local servers = require('navigator.lspclient.servers')
|
||||
|
||||
local lsp_installer_servers = {}
|
||||
local has_lspinst = false
|
||||
local has_mason = false
|
||||
|
||||
if config.lsp_installer == true then
|
||||
has_lspinst, _ = pcall(require, 'nvim-lsp-installer')
|
||||
if has_lspinst then
|
||||
local srvs = require('nvim-lsp-installer.servers').get_installed_servers()
|
||||
log('lsp_installered servers', srvs)
|
||||
if #srvs > 0 then
|
||||
lsp_installer_servers = srvs
|
||||
end
|
||||
has_lspinst, _ = pcall(require, 'nvim-lsp-installer')
|
||||
if has_lspinst then
|
||||
local srvs = require('nvim-lsp-installer.servers').get_installed_servers()
|
||||
if #srvs > 0 then
|
||||
lsp_installer_servers = srvs
|
||||
end
|
||||
log(lsp_installer_servers)
|
||||
end
|
||||
|
||||
has_mason, _ = pcall(require, 'mason-lspconfig')
|
||||
if has_mason then
|
||||
local srvs=require'mason-lspconfig'.get_installed_servers()
|
||||
if #srvs > 0 then
|
||||
lsp_installer_servers = srvs
|
||||
end
|
||||
end
|
||||
log("lsp_installer:", lsp_installer_servers)
|
||||
|
||||
if config.lsp.disable_lsp == 'all' then
|
||||
config.lsp.disable_lsp = servers
|
||||
end
|
||||
@ -393,8 +114,8 @@ local ng_default_cfg = {
|
||||
}
|
||||
|
||||
-- check and load based on file type
|
||||
local function load_cfg(ft, client, cfg, loaded)
|
||||
log(ft, client, loaded)
|
||||
local function load_cfg(ft, client, cfg, loaded, starting)
|
||||
log(ft, client, loaded, starting)
|
||||
trace(cfg)
|
||||
if lspconfig[client] == nil then
|
||||
log('not supported by nvim', client)
|
||||
@ -403,6 +124,7 @@ local function load_cfg(ft, client, cfg, loaded)
|
||||
|
||||
local lspft = lspconfig[client].document_config.default_config.filetypes
|
||||
local additional_ft = setups[client] and setups[client].filetypes or {}
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local cmd = cfg.cmd
|
||||
vim.list_extend(lspft, additional_ft)
|
||||
|
||||
@ -418,19 +140,46 @@ local function load_cfg(ft, client, cfg, loaded)
|
||||
end
|
||||
|
||||
trace('lsp for client', client, cfg)
|
||||
if cmd == nil or #cmd == 0 or vim.fn.executable(cmd[1]) == 0 then
|
||||
log('lsp not installed for client', client, cmd)
|
||||
if cmd == nil or #cmd == 0 or vfn.executable(cmd[1]) == 0 then
|
||||
log('lsp not installed for client', client, cmd, "fallback")
|
||||
return
|
||||
end
|
||||
if _NG_Loaded == nil then
|
||||
return log('_NG_Loaded not set')
|
||||
end
|
||||
|
||||
for k, c in pairs(loaded) do
|
||||
if client == k then
|
||||
-- loaded
|
||||
log(client, 'already been loaded for', ft, loaded, c)
|
||||
if not _NG_Loaded[bufnr] or _NG_Loaded[bufnr] < 4 then
|
||||
log('doautocmd filetype')
|
||||
vim.defer_fn(function()
|
||||
vim.cmd('doautocmd FileType')
|
||||
_NG_Loaded[bufnr] = (_NG_Loaded[bufnr] or 0 ) + 1
|
||||
end, 100)
|
||||
return
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
local clients = vim.lsp.buf_get_clients(0)
|
||||
for _, c in pairs(clients or {}) do
|
||||
log("lsp start up in progress client", client, c.name)
|
||||
if c.name == client then
|
||||
_NG_Loaded[bufnr] = 100
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
if starting and (starting.cnt or 0) > 0 then
|
||||
log("lsp start up in progress", starting)
|
||||
return vim.defer_fn(function()
|
||||
load_cfg(ft, client, cfg, loaded, { cnt = starting.cnt - 1 })
|
||||
end,
|
||||
200)
|
||||
end
|
||||
|
||||
if lspconfig[client] == nil then
|
||||
error('client ' .. client .. ' not supported')
|
||||
return
|
||||
@ -440,8 +189,27 @@ local function load_cfg(ft, client, cfg, loaded)
|
||||
log('lspconfig setup')
|
||||
-- log(lspconfig.available_servers())
|
||||
-- force reload with config
|
||||
lspconfig[client].setup(cfg)
|
||||
log(client, 'loading for', ft)
|
||||
-- lets have a guard here
|
||||
if not _NG_Loaded[client] then
|
||||
log(client, 'loading for', ft, cfg)
|
||||
log(lspconfig[client])
|
||||
lspconfig[client].setup(cfg)
|
||||
_NG_Loaded[client] = true
|
||||
vim.defer_fn(function()
|
||||
log('send filetype event')
|
||||
vim.cmd([[doautocmd Filetype]])
|
||||
_NG_Loaded[bufnr] = (_NG_Loaded[bufnr] or 0 )+ 1
|
||||
end, 400)
|
||||
else
|
||||
log('send filetype event')
|
||||
if not _NG_Loaded[bufnr] or _NG_Loaded[bufnr] < 4 then
|
||||
log('doautocmd filetype')
|
||||
vim.defer_fn(function()
|
||||
vim.cmd('doautocmd FileType')
|
||||
_NG_Loaded[bufnr] = (_NG_Loaded[bufnr] or 0 ) + 1
|
||||
end, 100)
|
||||
end
|
||||
end
|
||||
end
|
||||
-- need to verify the lsp server is up
|
||||
end
|
||||
@ -459,7 +227,7 @@ local function setup_fmt(client, enabled)
|
||||
client.server_capabilities.documentFormattingProvider = false
|
||||
else
|
||||
client.server_capabilities.documentFormattingProvider = client.server_capabilities.documentFormattingProvider
|
||||
or enabled
|
||||
or enabled
|
||||
end
|
||||
end
|
||||
|
||||
@ -485,7 +253,7 @@ end
|
||||
local loaded = {}
|
||||
local function lsp_startup(ft, retry, user_lsp_opts)
|
||||
retry = retry or false
|
||||
|
||||
local path_sep = require('navigator.util').path_sep()
|
||||
local capabilities = update_capabilities()
|
||||
|
||||
for _, lspclient in ipairs(servers) do
|
||||
@ -555,7 +323,7 @@ local function lsp_startup(ft, retry, user_lsp_opts)
|
||||
|
||||
log(lspclient)
|
||||
-- if user provides override values
|
||||
cfg.capabilities = capabilities
|
||||
-- cfg.capabilities = capabilities
|
||||
log(lspclient, config.lsp.disable_format_cap)
|
||||
if vim.tbl_contains(config.lsp.disable_format_cap or {}, lspclient) then
|
||||
log('fileformat disabled for ', lspclient)
|
||||
@ -639,16 +407,21 @@ local function lsp_startup(ft, retry, user_lsp_opts)
|
||||
|
||||
log('lsp installer server config ' .. lspconfig[lspclient].name, installer_cfg)
|
||||
if installed and installer_cfg then
|
||||
local paths = installer_cfg:get_default_options().cmd_env.PATH
|
||||
local paths = installer_cfg:get_default_options().cmd_env and installer_cfg:get_default_options().cmd_env.PATH
|
||||
if not paths then
|
||||
-- for some reason lspinstaller does not install the binary, check default PATH
|
||||
log('lsp installer does not install the lsp in its path, fallback')
|
||||
return load_cfg(ft, lspclient, cfg, loaded)
|
||||
end
|
||||
paths = vim.split(paths, ':')
|
||||
if vim.fn.empty(cfg.cmd) == 1 then
|
||||
if vfn.empty(cfg.cmd) == 1 then
|
||||
cfg.cmd = { installer_cfg.name }
|
||||
end
|
||||
|
||||
if vim.fn.executable(cfg.cmd[1]) == 0 then
|
||||
if vfn.executable(cfg.cmd[1]) == 0 then
|
||||
for _, path in ipairs(paths) do
|
||||
log(path)
|
||||
if vim.fn.isdirectory(path) == 1 and string.find(path, installer_cfg.root_dir) then
|
||||
if vfn.isdirectory(path) == 1 and string.find(path, installer_cfg.root_dir) then
|
||||
cfg.cmd[1] = path .. path_sep .. cfg.cmd[1]
|
||||
log(cfg.cmd)
|
||||
break
|
||||
@ -660,17 +433,49 @@ local function lsp_startup(ft, retry, user_lsp_opts)
|
||||
end
|
||||
end
|
||||
end
|
||||
if has_mason and _NgConfigValues.mason then
|
||||
local servers = require'mason-lspconfig'.get_installed_servers()
|
||||
if not vim.tbl_contains(servers, lspconfig[lspclient].name) then
|
||||
log('mason server not installed', lspconfig[lspclient].name)
|
||||
-- return
|
||||
end
|
||||
local pkg_name = require "mason-lspconfig.mappings.server".lspconfig_to_package[lspconfig[lspclient].name]
|
||||
local pkg = require "mason-registry".get_package(pkg_name)
|
||||
|
||||
if vim.fn.executable(cfg.cmd[1]) == 0 then
|
||||
log('lsp installer server config ' .. lspconfig[lspclient].name, pkg)
|
||||
if pkg then
|
||||
local path = pkg:get_install_path()
|
||||
if not path then
|
||||
-- for some reason lspinstaller does not install the binary, check default PATH
|
||||
log('lsp installer does not install the lsp in its path, fallback')
|
||||
return load_cfg(ft, lspclient, cfg, loaded)
|
||||
end
|
||||
|
||||
cfg.cmd = cfg.cmd or {}
|
||||
cfg.cmd[1] = table.concat({vfn.stdpath('data'), 'mason', 'bin', pkg.name}, path_sep)
|
||||
if vfn.executable(cfg.cmd[1]) == 0 then
|
||||
log('failed to find cmd', cfg.cmd[1], "fallback")
|
||||
return load_cfg(ft, lspclient, cfg, loaded)
|
||||
else
|
||||
log('cmd installed', cfg.cmd)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
if vfn.executable(cfg.cmd[1]) == 0 then
|
||||
log('lsp server not installed in path ' .. lspclient .. vim.inspect(cfg.cmd), vim.lsp.log_levels.WARN)
|
||||
end
|
||||
|
||||
if _NG_Loaded[lspclient] then
|
||||
log('client loaded ?', lspclient)
|
||||
log('client loaded ?', lspclient, _NG_Loaded[lspclient])
|
||||
end
|
||||
local starting = {}
|
||||
if _NG_Loaded[lspclient] == true then
|
||||
starting = { cnt = 1 }
|
||||
end
|
||||
load_cfg(ft, lspclient, cfg, loaded)
|
||||
|
||||
_NG_Loaded[lspclient] = true
|
||||
load_cfg(ft, lspclient, cfg, loaded, starting)
|
||||
-- load_cfg(ft, lspclient, {}, loaded)
|
||||
::continue::
|
||||
end
|
||||
@ -744,7 +549,7 @@ local function setup(user_opts, cnt)
|
||||
local bufnr = user_opts.bufnr or vim.api.nvim_get_current_buf()
|
||||
if ft == '' or ft == nil then
|
||||
log('nil filetype, callback')
|
||||
local ext = vim.fn.expand('%:e')
|
||||
local ext = vfn.expand('%:e')
|
||||
if ext ~= '' then
|
||||
cnt = cnt or 0
|
||||
local opts = vim.deepcopy(user_opts)
|
||||
@ -824,7 +629,7 @@ local function setup(user_opts, cnt)
|
||||
|
||||
--- if code lens enabled
|
||||
if _NgConfigValues.lsp.code_lens_action.enable then
|
||||
require('navigator.codelens').setup()
|
||||
require('navigator.codelens').setup(bufnr)
|
||||
end
|
||||
|
||||
-- _LoadedFiletypes[ft .. tostring(bufnr)] = true -- may prevent lsp config when reboot lsp
|
||||
@ -839,23 +644,38 @@ local function on_filetype()
|
||||
return
|
||||
end
|
||||
if uri == 'file://' or uri == 'file:///' then
|
||||
log('skip loading for ft ', ft, uri)
|
||||
trace('skip loading for ft ', ft, uri)
|
||||
return
|
||||
end
|
||||
|
||||
log (_NG_Loaded)
|
||||
if _NG_Loaded[bufnr] and type(_NG_Loaded[bufnr]) == 'number' and _NG_Loaded[bufnr] > 1 then
|
||||
log('navigator was loaded for ft', ft, bufnr)
|
||||
return
|
||||
end
|
||||
|
||||
-- on_filetype should only be trigger only once for each bufnr
|
||||
if _NG_Loaded[bufnr] ~= nil and type(_NG_Loaded[bufnr] == 'number') then
|
||||
_NG_Loaded[bufnr] = _NG_Loaded[bufnr] + 1 -- do not hook and trigger filetype event multiple times
|
||||
end
|
||||
if _NG_Loaded[bufnr] == true then
|
||||
_NG_Loaded[bufnr] = 1 -- record the count
|
||||
end
|
||||
|
||||
-- as setup will send filetype event as well
|
||||
log(uri)
|
||||
|
||||
local wids = vim.fn.win_findbuf(bufnr)
|
||||
local wids = vfn.win_findbuf(bufnr)
|
||||
if empty(wids) then
|
||||
log('buf not shown return')
|
||||
end
|
||||
setup({ bufnr = bufnr })
|
||||
_NG_Loaded[bufnr] = 1
|
||||
end
|
||||
|
||||
return {
|
||||
setup = setup,
|
||||
get_cfg = get_cfg,
|
||||
lsp = servers,
|
||||
add_servers = add_servers,
|
||||
on_filetype = on_filetype,
|
||||
disabled_ft = disabled_ft,
|
||||
|
191
lua/navigator/lspclient/clients_default.lua
Normal file
191
lua/navigator/lspclient/clients_default.lua
Normal file
@ -0,0 +1,191 @@
|
||||
local M = {}
|
||||
local vfn = vim.fn
|
||||
M.defaults = function()
|
||||
local has_lsp, lspconfig = pcall(require, 'lspconfig')
|
||||
local highlight = require('navigator.lspclient.highlight')
|
||||
if not has_lsp then
|
||||
return {
|
||||
setup = function()
|
||||
vim.notify('loading lsp config failed LSP may not working correctly', vim.lsp.log_levels.WARN)
|
||||
end,
|
||||
}
|
||||
end
|
||||
local util = lspconfig.util
|
||||
local on_attach = require('navigator.lspclient.attach').on_attach
|
||||
|
||||
|
||||
local setups = {
|
||||
clojure_lsp = {
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('deps.edn', 'build.boot', 'project.clj', 'shadow-cljs.edn', 'bb.edn', '.git')(fname)
|
||||
or util.path.dirname(fname)
|
||||
end,
|
||||
on_attach = on_attach,
|
||||
filetypes = { 'clojure', 'edn' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
cmd = { 'clojure-lsp' },
|
||||
},
|
||||
|
||||
elixirls = {
|
||||
on_attach = on_attach,
|
||||
filetypes = { 'elixir', 'eelixir' },
|
||||
cmd = { 'elixir-ls' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
settings = {
|
||||
elixirLS = {
|
||||
dialyzerEnabled = true,
|
||||
fetchDeps = false,
|
||||
},
|
||||
},
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('mix.exs', '.git')(fname) or util.path.dirname(fname)
|
||||
end,
|
||||
},
|
||||
|
||||
gopls = {
|
||||
on_attach = on_attach,
|
||||
-- capabilities = cap,
|
||||
filetypes = { 'go', 'gomod', 'gohtmltmpl', 'gotexttmpl' },
|
||||
message_level = vim.lsp.protocol.MessageType.Error,
|
||||
cmd = {
|
||||
'gopls', -- share the gopls instance if there is one already
|
||||
'-remote=auto', --[[ debug options ]] --
|
||||
-- "-logfile=auto",
|
||||
-- "-debug=:0",
|
||||
'-remote.debug=:0',
|
||||
-- "-rpc.trace",
|
||||
},
|
||||
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 1000 },
|
||||
settings = {
|
||||
gopls = {
|
||||
-- more settings: https://github.com/golang/tools/blob/master/gopls/doc/settings.md
|
||||
-- flags = {allow_incremental_sync = true, debounce_text_changes = 500},
|
||||
-- not supported
|
||||
analyses = { unusedparams = true, unreachable = false },
|
||||
codelenses = {
|
||||
generate = true, -- show the `go generate` lens.
|
||||
gc_details = true, -- // Show a code lens toggling the display of gc's choices.
|
||||
test = true,
|
||||
tidy = true,
|
||||
},
|
||||
usePlaceholders = true,
|
||||
completeUnimported = true,
|
||||
staticcheck = true,
|
||||
matcher = 'fuzzy',
|
||||
diagnosticsDelay = '500ms',
|
||||
experimentalWatchedFileDelay = '1000ms',
|
||||
symbolMatcher = 'fuzzy',
|
||||
gofumpt = false, -- true, -- turn on for new repos, gofmpt is good but also create code turmoils
|
||||
buildFlags = { '-tags', 'integration' },
|
||||
-- buildFlags = {"-tags", "functional"}
|
||||
},
|
||||
},
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('go.mod', '.git')(fname) or dirname(fname) -- util.path.dirname(fname)
|
||||
end,
|
||||
},
|
||||
clangd = {
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
cmd = {
|
||||
'clangd',
|
||||
'--background-index',
|
||||
'--suggest-missing-includes',
|
||||
'--clang-tidy',
|
||||
'--header-insertion=iwyu',
|
||||
'--clang-tidy-checks=-*,llvm-*,clang-analyzer-*',
|
||||
'--cross-file-rename',
|
||||
},
|
||||
filetypes = { 'c', 'cpp', 'objc', 'objcpp' },
|
||||
on_attach = function(client, bufnr)
|
||||
client.server_capabilities.documentFormattingProvider = client.server_capabilities.documentFormattingProvider
|
||||
or true
|
||||
on_attach(client, bufnr)
|
||||
end,
|
||||
},
|
||||
rust_analyzer = {
|
||||
root_dir = function(fname)
|
||||
return util.root_pattern('Cargo.toml', 'rust-project.json', '.git')(fname) or util.path.dirname(fname)
|
||||
end,
|
||||
filetypes = { 'rust' },
|
||||
message_level = vim.lsp.protocol.MessageType.error,
|
||||
on_attach = on_attach,
|
||||
settings = {
|
||||
['rust-analyzer'] = {
|
||||
assist = { importMergeBehavior = 'last', importPrefix = 'by_self' },
|
||||
cargo = { loadOutDirsFromCheck = true },
|
||||
procMacro = { enable = true },
|
||||
},
|
||||
},
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
},
|
||||
sqls = {
|
||||
filetypes = { 'sql' },
|
||||
on_attach = function(client, _)
|
||||
client.server_capabilities.executeCommandProvider = client.server_capabilities.documentFormattingProvider
|
||||
or true
|
||||
highlight.diagnositc_config_sign()
|
||||
require('sqls').setup({ picker = 'telescope' }) -- or default
|
||||
end,
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
cmd = { 'sqls', '-config', '$HOME/.config/sqls/config.yml' },
|
||||
-- alterantively:
|
||||
-- connections = {
|
||||
-- {
|
||||
-- driver = 'postgresql',
|
||||
-- datasourcename = 'host=127.0.0.1 port=5432 user=postgres password=password dbname=user_db sslmode=disable',
|
||||
-- },
|
||||
-- },
|
||||
},
|
||||
},
|
||||
|
||||
pyright = {
|
||||
on_attach = on_attach,
|
||||
cmd = { 'pyright-langserver', '--stdio' },
|
||||
filetypes = { 'python' },
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
python = {
|
||||
formatting = { provider = 'black' },
|
||||
analysis = {
|
||||
autoSearchPaths = true,
|
||||
useLibraryCodeForTypes = true,
|
||||
diagnosticMode = 'workspace',
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
ccls = {
|
||||
on_attach = on_attach,
|
||||
init_options = {
|
||||
compilationDatabaseDirectory = 'build',
|
||||
root_dir = [[ util.root_pattern("compile_commands.json", "compile_flags.txt", "CMakeLists.txt", "Makefile", ".git") or util.path.dirname ]],
|
||||
index = { threads = 2 },
|
||||
clang = { excludeArgs = { '-frounding-math' } },
|
||||
},
|
||||
flags = { allow_incremental_sync = true },
|
||||
},
|
||||
jdtls = {
|
||||
settings = {
|
||||
java = { signatureHelp = { enabled = true }, contentProvider = { preferred = 'fernflower' } },
|
||||
},
|
||||
},
|
||||
omnisharp = {
|
||||
cmd = { 'omnisharp', '--languageserver', '--hostPID', tostring(vfn.getpid()) },
|
||||
},
|
||||
terraformls = {
|
||||
filetypes = { 'terraform', 'tf' },
|
||||
},
|
||||
|
||||
sourcekit = {
|
||||
cmd = { 'sourcekit-lsp' },
|
||||
filetypes = { 'swift' }, -- This is recommended if you have separate settings for clangd.
|
||||
},
|
||||
}
|
||||
|
||||
setups.sumneko_lua = require('navigator.lspclient.sumneko_lua').sumneko_lua()
|
||||
return setups
|
||||
end
|
||||
|
||||
return M
|
@ -1,5 +1,3 @@
|
||||
local lsp = require("vim.lsp")
|
||||
|
||||
local M = {}
|
||||
local capabilities = vim.lsp.protocol.make_client_capabilities()
|
||||
capabilities.textDocument.completion.completionItem.snippetSupport = true
|
||||
|
@ -3,6 +3,7 @@ local M = {}
|
||||
-- local log = require('navigator.util').log
|
||||
local api = vim.api
|
||||
|
||||
local cmd_group = api.nvim_create_augroup('NGHiGroup', {})
|
||||
-- lsp sign ﮻ ﯭ ﳀ
|
||||
function M.diagnositc_config_sign()
|
||||
if M.configed then
|
||||
@ -31,35 +32,41 @@ function M.diagnositc_config_sign()
|
||||
M.configed = true
|
||||
end
|
||||
|
||||
local colors = {
|
||||
{ '#aefe00', '#aede00', '#aebe00', '#4e7efe' },
|
||||
{ '#ff00e0', '#df00e0', '#af00e0', '#fedefe' },
|
||||
{ '#1000ef', '#2000df', '#2000cf', '#f0f040' },
|
||||
{ '#d8a8a3', '#c8a8a3', '#b8a8a3', '#4e2c33' },
|
||||
{ '#ffa724', '#efa024', '#dfa724', '#0040ff' },
|
||||
{ '#afdc2b', '#09dc4b', '#08d04b', '#ef4f8f' },
|
||||
}
|
||||
|
||||
function M.add_highlight()
|
||||
-- lsp system default
|
||||
api.nvim_command('hi! link DiagnosticUnderlineError SpellBad')
|
||||
api.nvim_command('hi! link DiagnosticUnderlineWarning SpellRare')
|
||||
api.nvim_command('hi! link DiagnosticUnderlineInformation SpellRare')
|
||||
api.nvim_command('hi! link DiagnosticUnderlineHint SpellRare')
|
||||
api.nvim_command('hi def link NGPreviewTitle Title')
|
||||
local colors = {
|
||||
{ '#aefe00', '#aede00', '#aebe00', '#4e7efe' },
|
||||
{ '#ff00e0', '#df00e0', '#af00e0', '#fedefe' },
|
||||
{ '#1000ef', '#2000df', '#2000cf', '#f0f040' },
|
||||
{ '#d8a8a3', '#c8a8a3', '#b8a8a3', '#4e2c33' },
|
||||
{ '#ffa724', '#efa024', '#dfa724', '#0040ff' },
|
||||
{ '#afdc2b', '#09dc4b', '#08d04b', '#ef4f8f' },
|
||||
}
|
||||
|
||||
api.nvim_set_hl(0, 'DiagnosticUnderlineError', { link = 'SpellBad', default = true })
|
||||
api.nvim_set_hl(0, 'DiagnosticUnderlineWarning', { link = 'SpellRare', default = true })
|
||||
api.nvim_set_hl(0, 'DiagnosticUnderlineInformation', { link = 'SpellRare', default = true })
|
||||
api.nvim_set_hl(0, 'DiagnosticUnderlineHint', { link = 'SpellRare', default = true })
|
||||
api.nvim_set_hl(0, 'NGPreviewTitle', { link = 'Title', default = true })
|
||||
api.nvim_set_hl(0, 'LspReferenceRead', { default = true, link = 'IncSearch'})
|
||||
api.nvim_set_hl(0, 'LspReferenceText', { default = true, link = 'Visual'})
|
||||
api.nvim_set_hl( 0, 'LspReferenceWrite', { default = true, link = 'Search'})
|
||||
|
||||
for i = 1, #colors do
|
||||
for j = 1, 3 do
|
||||
local cmd = string.format('hi! default NGHiReference_%i_%i guibg=%s guifg=%s ', i, j, colors[i][j], colors[i][4])
|
||||
vim.cmd(cmd)
|
||||
local hlg = string.format('NGHiReference_%i_%i', i, j) -- , colors[i][j], colors[i][4]
|
||||
api.nvim_set_hl(0, hlg, { fg = colors[i][j], bg = colors[i][4], default = true })
|
||||
end
|
||||
end
|
||||
|
||||
vim.cmd([[
|
||||
autocmd ColorScheme * |
|
||||
hi default LspReferenceRead cterm=bold gui=Bold ctermbg=yellow guifg=yellow guibg=purple4 |
|
||||
hi default LspReferenceText cterm=bold gui=Bold ctermbg=red guifg=SlateBlue guibg=MidnightBlue |
|
||||
hi default LspReferenceWrite cterm=bold gui=Bold,Italic ctermbg=red guifg=DarkSlateBlue guibg=MistyRose
|
||||
]])
|
||||
end
|
||||
|
||||
api.nvim_create_autocmd('ColorScheme', {
|
||||
group = cmd_group,
|
||||
pattern = '*',
|
||||
callback = function()
|
||||
M.add_highlight()
|
||||
end,
|
||||
})
|
||||
|
||||
return M
|
||||
|
@ -3,12 +3,6 @@ local log = util.log
|
||||
local trace = util.trace
|
||||
local api = vim.api
|
||||
|
||||
local event_hdlrs = {
|
||||
{ ev = 'BufWritePre', func = require('navigator.diagnostics').set_diag_loclist },
|
||||
{ ev = { 'CursorHold', 'CursorHoldI' }, func = vim.lsp.buf.document_highlight },
|
||||
{ ev = 'CursorMoved', func = vim.lsp.buf.clear_references },
|
||||
}
|
||||
|
||||
if vim.lsp.buf.format == nil then
|
||||
vim.lsp.buf.format = vim.lsp.buf.formatting
|
||||
end
|
||||
@ -67,22 +61,16 @@ local key_maps = {
|
||||
},
|
||||
{ key = '<Space>ff', func = vim.lsp.buf.format, mode = 'n', desc = 'format' },
|
||||
{ key = '<Space>ff', func = vim.lsp.buf.range_formatting, mode = 'v', desc = 'range format' },
|
||||
{ key = '<Space>rf', func = require('navigator.formatting').range_format, mode = 'n', desc = 'range_fmt_v' },
|
||||
{
|
||||
key = '<Space>gm',
|
||||
func = require('navigator.formatting').range_format,
|
||||
mode = 'n',
|
||||
desc = 'range format operator e.g gmip',
|
||||
},
|
||||
{ key = '<Space>wl', func = require('navigator.workspace').list_workspace_folders, desc = 'list_workspace_folders' },
|
||||
{ key = '<Space>la', mode = 'n', func = require('navigator.codelens').run_action, desc = 'run code lens action' },
|
||||
}
|
||||
|
||||
local commands = {
|
||||
[[command! -nargs=* Nctags lua require("navigator.ctags").ctags(<f-args>)]],
|
||||
"command! -nargs=0 LspLog lua require'navigator.lspclient.config'.open_lsp_log()",
|
||||
"command! -nargs=0 LspRestart lua require'navigator.lspclient.config'.reload_lsp()",
|
||||
"command! -nargs=0 LspToggleFmt lua require'navigator.lspclient.mapping'.toggle_lspformat()<CR>",
|
||||
"command! -nargs=0 LspKeymaps lua require'navigator.lspclient.mapping'.get_keymaps_help()<CR>",
|
||||
"command! -nargs=0 LspSymbols lua require'navigator.symbols'.side_panel()<CR>",
|
||||
"command! -nargs=0 TSymbols lua require'navigator.treesitter'.side_panel()<CR>",
|
||||
"command! -nargs=* Calltree lua require'navigator.hierarchy'.calltree(<f-args>)<CR>",
|
||||
}
|
||||
|
||||
local key_maps_help = {}
|
||||
-- LuaFormatter on
|
||||
local M = {}
|
||||
@ -127,6 +115,18 @@ local check_cap = function(opts)
|
||||
end
|
||||
|
||||
local function set_cmds(_)
|
||||
local commands = {
|
||||
[[command! -nargs=* Nctags lua require("navigator.ctags").ctags(<f-args>)]],
|
||||
"command! -nargs=0 LspLog lua require'navigator.lspclient.config'.open_lsp_log()",
|
||||
"command! -nargs=0 LspRestart lua require'navigator.lspclient.config'.reload_lsp()",
|
||||
"command! -nargs=0 LspToggleFmt lua require'navigator.lspclient.mapping'.toggle_lspformat()<CR>",
|
||||
"command! -nargs=0 LspKeymaps lua require'navigator.lspclient.mapping'.get_keymaps_help()<CR>",
|
||||
"command! -nargs=0 LspSymbols lua require'navigator.symbols'.side_panel()<CR>",
|
||||
"command! -nargs=0 TSymbols lua require'navigator.treesitter'.side_panel()<CR>",
|
||||
"command! -nargs=0 NRefPanel lua require'navigator.reference'.side_panel()<CR>",
|
||||
"command! -nargs=* Calltree lua require'navigator.hierarchy'.calltree(<f-args>)<CR>",
|
||||
}
|
||||
|
||||
for _, value in pairs(commands) do
|
||||
vim.cmd(value)
|
||||
end
|
||||
@ -183,7 +183,8 @@ local function set_mapping(lsp_attach_info)
|
||||
key_maps = _NgConfigValues.keymaps or {}
|
||||
log('setting maps to ', key_maps)
|
||||
end
|
||||
local fmtkey, rfmtkey
|
||||
local fmtkey, rfmtkey, nrfmtkey
|
||||
require('navigator.formatting')
|
||||
for _, value in pairs(key_maps) do
|
||||
if value.doc then
|
||||
vim.notify('doc field no longer supported in navigator mapping, use desc instead')
|
||||
@ -216,15 +217,18 @@ local function set_mapping(lsp_attach_info)
|
||||
if value.desc then
|
||||
opts.desc = value.desc
|
||||
end
|
||||
opts.buffer = bufnr
|
||||
vim.keymap.set(value.mode or 'n', value.key, value.func, opts)
|
||||
if string.find(value.desc, 'range format') then
|
||||
if string.find(value.desc, 'range format') and value.mode == 'v' then
|
||||
rfmtkey = value.key
|
||||
elseif string.find(value.desc, 'format') then
|
||||
fmtkey = value.key
|
||||
if string.find(value.desc, 'range format') and value.mode == 'n' then
|
||||
nrfmtkey = value.key
|
||||
elseif string.find(value.desc, 'format') then
|
||||
fmtkey = value.key
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
for _, val in pairs(key_maps) do
|
||||
local helper_msg = ''
|
||||
if val.desc then
|
||||
@ -270,6 +274,9 @@ local function set_mapping(lsp_attach_info)
|
||||
del_keymap('v', rfmtkey)
|
||||
end
|
||||
|
||||
if not range_fmt and nrfmtkey then
|
||||
del_keymap('n', nrfmtkey)
|
||||
end
|
||||
log('enable format ', doc_fmt, range_fmt, _NgConfigValues.lsp.format_on_save)
|
||||
end
|
||||
|
||||
@ -282,42 +289,6 @@ local function autocmd()
|
||||
})
|
||||
end
|
||||
|
||||
local function set_event_handler(user_opts)
|
||||
user_opts = user_opts or {}
|
||||
local file_types = {
|
||||
'*.c',
|
||||
'*.cpp',
|
||||
'*.h',
|
||||
'*.go',
|
||||
'*.python',
|
||||
'*.vim',
|
||||
'*.sh',
|
||||
'*.javascript',
|
||||
'*.html',
|
||||
'*.css',
|
||||
'*.lua',
|
||||
'*.typescript',
|
||||
'*.rust',
|
||||
'*.javascriptreact',
|
||||
'*.typescriptreact',
|
||||
'*.kotlin',
|
||||
'*.php',
|
||||
'*.dart',
|
||||
'*.nim',
|
||||
'*.java',
|
||||
}
|
||||
-- local format_files = "c,cpp,h,go,python,vim,javascript,typescript" --html,css,
|
||||
|
||||
local gn = api.nvim_create_augroup('nvim_nv_event_autos', {})
|
||||
for _, value in pairs(event_hdlrs) do
|
||||
api.nvim_create_autocmd(value.ev, {
|
||||
group = gn,
|
||||
pattern = file_types,
|
||||
callback = value.func,
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
M.toggle_lspformat = function(on)
|
||||
if on == nil then
|
||||
_NgConfigValues.lsp.format_on_save = not _NgConfigValues.lsp.format_on_save
|
||||
@ -349,7 +320,6 @@ function M.setup(attach_opts)
|
||||
set_cmds(attach_opts)
|
||||
|
||||
autocmd()
|
||||
set_event_handler(attach_opts)
|
||||
|
||||
local client = attach_opts.client or {}
|
||||
local cap = client.server_capabilities or vim.lsp.protocol.make_client_capabilities()
|
||||
@ -392,6 +362,14 @@ function M.setup(attach_opts)
|
||||
})
|
||||
end
|
||||
|
||||
api.nvim_create_autocmd({ 'BufWritePre' }, {
|
||||
group = api.nvim_create_augroup('nvim_nv_event_autos', {}),
|
||||
buffer = attach_opts.bufnr,
|
||||
callback = function()
|
||||
require('navigator.diagnostics').set_diag_loclist(attach_opts.bufnr)
|
||||
end,
|
||||
})
|
||||
|
||||
local border_style = single
|
||||
if _NgConfigValues.border == 'double' then
|
||||
border_style = double
|
||||
|
47
lua/navigator/lspclient/servers.lua
Normal file
47
lua/navigator/lspclient/servers.lua
Normal file
@ -0,0 +1,47 @@
|
||||
return {
|
||||
'angularls',
|
||||
'gopls',
|
||||
'tsserver',
|
||||
'flow',
|
||||
'bashls',
|
||||
'dockerls',
|
||||
'julials',
|
||||
'pylsp',
|
||||
'pyright',
|
||||
'jedi_language_server',
|
||||
'jdtls',
|
||||
'sumneko_lua',
|
||||
'vimls',
|
||||
'html',
|
||||
'jsonls',
|
||||
'solargraph',
|
||||
'cssls',
|
||||
'yamlls',
|
||||
'clangd',
|
||||
'ccls',
|
||||
'sqls',
|
||||
'denols',
|
||||
'graphql',
|
||||
'dartls',
|
||||
'dotls',
|
||||
'kotlin_language_server',
|
||||
'nimls',
|
||||
'intelephense',
|
||||
'vuels',
|
||||
'volar',
|
||||
'phpactor',
|
||||
'omnisharp',
|
||||
'r_language_server',
|
||||
'rust_analyzer',
|
||||
'terraformls',
|
||||
'svelte',
|
||||
'texlab',
|
||||
'clojure_lsp',
|
||||
'elixirls',
|
||||
'sourcekit',
|
||||
'fsautocomplete',
|
||||
'vls',
|
||||
'hls',
|
||||
'tflint',
|
||||
'terraform_lsp',
|
||||
}
|
89
lua/navigator/lspclient/sumneko_lua.lua
Normal file
89
lua/navigator/lspclient/sumneko_lua.lua
Normal file
@ -0,0 +1,89 @@
|
||||
local vfn = vim.fn
|
||||
|
||||
local library = {}
|
||||
local sumneko_cfg = {
|
||||
cmd = { 'lua-language-server' },
|
||||
filetypes = { 'lua' },
|
||||
on_attach = on_attach,
|
||||
flags = { allow_incremental_sync = true, debounce_text_changes = 500 },
|
||||
settings = {
|
||||
Lua = {
|
||||
runtime = {
|
||||
-- Tell the language server which version of Lua you're using (most likely LuaJIT in the case of Neovim)
|
||||
version = 'LuaJIT',
|
||||
},
|
||||
diagnostics = {
|
||||
enable = true,
|
||||
-- Get the language server to recognize the `vim` global
|
||||
globals = { 'vim', 'describe', 'it', 'before_each', 'after_each', 'teardown', 'pending' },
|
||||
},
|
||||
completion = { callSnippet = 'Both' },
|
||||
workspace = {
|
||||
-- Make the server aware of Neovim runtime files
|
||||
library = library,
|
||||
maxPreload = 2000,
|
||||
preloadFileSize = 40000,
|
||||
},
|
||||
telemetry = { enable = false },
|
||||
},
|
||||
},
|
||||
on_new_config = function(cfg, root)
|
||||
local libs = vim.tbl_deep_extend('force', {}, library)
|
||||
libs[root] = nil
|
||||
cfg.settings.Lua.workspace.library = libs
|
||||
return cfg
|
||||
end,
|
||||
}
|
||||
|
||||
local function add(lib)
|
||||
for _, p in pairs(vfn.expand(lib, false, true)) do
|
||||
p = vim.loop.fs_realpath(p)
|
||||
if p then
|
||||
library[p] = true
|
||||
end
|
||||
end
|
||||
end
|
||||
local function sumneko_lua()
|
||||
-- add runtime
|
||||
-- add plugins it may be very slow to add all in path
|
||||
add('$VIMRUNTIME')
|
||||
-- add your config
|
||||
-- local home = vfn.expand("$HOME")
|
||||
add(vfn.stdpath('config'))
|
||||
|
||||
library[vfn.expand('$VIMRUNTIME/lua')] = true
|
||||
library[vfn.expand('$VIMRUNTIME/lua/vim')] = true
|
||||
library[vfn.expand('$VIMRUNTIME/lua/vim/lsp')] = true
|
||||
|
||||
local on_attach = require('navigator.lspclient.attach').on_attach
|
||||
local luadevcfg = {
|
||||
library = {
|
||||
vimruntime = true, -- runtime path
|
||||
types = true, -- full signature, docs and completion of vim.api, vim.treesitter, vim.lsp and others
|
||||
plugins = { 'nvim-treesitter', 'plenary.nvim' },
|
||||
},
|
||||
lspconfig = {
|
||||
-- cmd = {sumneko_binary},
|
||||
on_attach = on_attach,
|
||||
},
|
||||
}
|
||||
|
||||
local luadev = {}
|
||||
local user_luadev = _NgConfigValues.lsp['lua-dev']
|
||||
if user_luadev then
|
||||
luadevcfg = vim.tbl_deep_extend('force', luadevcfg, user_luadev)
|
||||
end
|
||||
require('navigator.lazyloader').load('lua-dev.nvim', 'folke/lua-dev.nvim')
|
||||
|
||||
local ok, l = pcall(require, 'lua-dev')
|
||||
if ok and l then
|
||||
luadev = l.setup(luadevcfg)
|
||||
end
|
||||
|
||||
sumneko_cfg = vim.tbl_deep_extend('force', sumneko_cfg, luadev)
|
||||
return sumneko_cfg
|
||||
end
|
||||
|
||||
return {
|
||||
sumneko_lua = sumneko_lua,
|
||||
}
|
@ -19,7 +19,7 @@ cwd = gutil.add_pec(cwd)
|
||||
local ts_nodes = require('navigator.lru').new(1000, 1024 * 1024)
|
||||
local ts_nodes_time = require('navigator.lru').new(1000)
|
||||
local TS_analysis_enabled = require('navigator').config_values().treesitter_analysis
|
||||
|
||||
local nts = require('navigator.treesitter')
|
||||
-- extract symbol from range
|
||||
function M.get_symbol(text, range)
|
||||
if range == nil then
|
||||
@ -169,7 +169,7 @@ local function ts_functions(uri, optional)
|
||||
lerr('ts not enabled')
|
||||
return nil
|
||||
end
|
||||
local ts_func = require('navigator.treesitter').buf_func
|
||||
local ts_func = nts.buf_func
|
||||
local bufnr = vim.uri_to_bufnr(uri)
|
||||
local x = os.clock()
|
||||
trace(ts_nodes)
|
||||
@ -230,7 +230,7 @@ local function ts_definition(uri, range, optional)
|
||||
if optional then
|
||||
return
|
||||
end
|
||||
local ts_def = require('navigator.treesitter').find_definition
|
||||
local ts_def = nts.find_definition
|
||||
local bufnr = vim.uri_to_bufnr(uri)
|
||||
local x = os.clock()
|
||||
trace(ts_nodes)
|
||||
@ -252,6 +252,7 @@ local function ts_definition(uri, range, optional)
|
||||
end
|
||||
|
||||
local function find_ts_func_by_range(funcs, range)
|
||||
log(funcs, range)
|
||||
if funcs == nil or range == nil then
|
||||
return nil
|
||||
end
|
||||
@ -352,7 +353,6 @@ function M.locations_to_items(locations, ctx)
|
||||
|
||||
local unload_bufnrs = {}
|
||||
for i, loc in ipairs(locations) do
|
||||
local funcs = nil
|
||||
local item = lsp.util.locations_to_items({ loc }, enc)[1]
|
||||
item.range = locations[i].range or locations[i].targetRange
|
||||
item.uri = locations[i].uri or locations[i].targetUri
|
||||
@ -363,13 +363,25 @@ function M.locations_to_items(locations, ctx)
|
||||
log(cwd)
|
||||
end
|
||||
-- only load top 30 file.
|
||||
local proj_file = item.uri:find(cwd) or is_win or i < 30
|
||||
local proj_file = item.uri:find(cwd) or is_win or i < _NgConfigValues.treesitter_analysis_max_num
|
||||
local unload, def
|
||||
if TS_analysis_enabled and proj_file then
|
||||
funcs, unload = ts_functions(item.uri, ts_optional(i, #unload_bufnrs))
|
||||
local context = ''
|
||||
if TS_analysis_enabled and proj_file and not ctx.no_show then
|
||||
local ts_context = nts.ref_context
|
||||
|
||||
local bufnr = vim.uri_to_bufnr(item.uri)
|
||||
if not api.nvim_buf_is_loaded(bufnr) then
|
||||
log('! load buf !', item.uri, bufnr)
|
||||
vim.fn.bufload(bufnr)
|
||||
unload = bufnr
|
||||
end
|
||||
context = ts_context({ bufnr = bufnr, pos = item.range }) or ''
|
||||
log(context)
|
||||
|
||||
-- TODO: unload buffers
|
||||
if unload then
|
||||
table.insert(unload_bufnrs, unload)
|
||||
unload = nil
|
||||
end
|
||||
if not uri_def[item.uri] then
|
||||
-- find def in file
|
||||
@ -408,9 +420,15 @@ function M.locations_to_items(locations, ctx)
|
||||
end
|
||||
|
||||
item.filename = assert(vim.uri_to_fname(item.uri))
|
||||
|
||||
local filename = item.filename:gsub(cwd .. path_sep, path_cur, 1)
|
||||
|
||||
if ctx.no_show then
|
||||
local shorten = require('guihua.util').shorten
|
||||
filename = shorten(filename)
|
||||
end
|
||||
item.display_filename = filename or item.filename
|
||||
item.call_by = find_ts_func_by_range(funcs, item.range)
|
||||
item.call_by = context -- find_ts_func_by_range(funcs, item.range)
|
||||
item.rpath = util.get_relative_path(cwd, item.filename)
|
||||
width = math.max(width, #item.text)
|
||||
item.symbol_name = M.get_symbol(item.text, item.range)
|
||||
|
@ -11,10 +11,11 @@ local locations_to_items = lsphelper.locations_to_items
|
||||
|
||||
local M = {}
|
||||
local ref_view = function(err, locations, ctx, cfg)
|
||||
cfg = cfg or {}
|
||||
local truncate = cfg and cfg.truncate or 20
|
||||
local opts = {}
|
||||
trace('arg1', err, ctx, locations)
|
||||
log(#locations, locations[1])
|
||||
-- log(#locations, locations[1])
|
||||
if ctx.combine then
|
||||
-- wait for both reference and definition LSP request
|
||||
if ctx.results == nil then
|
||||
@ -41,27 +42,16 @@ local ref_view = function(err, locations, ctx, cfg)
|
||||
end
|
||||
vim.list_extend(locations, definitions.result)
|
||||
end
|
||||
|
||||
if references and references.result and #references.result > 0 then
|
||||
local refs = references.result
|
||||
for _, value in pairs(locations) do
|
||||
local vrange = value.range or { start = { line = 0 }, ['end'] = { line = 0 } }
|
||||
for i = 1, #refs, 1 do
|
||||
local rg = refs[i].range or {}
|
||||
trace(value, refs[i])
|
||||
trace(rg, vrange)
|
||||
if rg.start.line == vrange.start.line and rg['end'].line == vrange['end'].line then
|
||||
table.remove(refs, i)
|
||||
break
|
||||
end
|
||||
end
|
||||
end
|
||||
vim.list_extend(locations, refs)
|
||||
end
|
||||
err = nil
|
||||
trace(locations)
|
||||
-- lets de-dup first 10 elements. some lsp does not recognize definition and reference difference
|
||||
locations = util.dedup(locations)
|
||||
|
||||
trace(locations)
|
||||
end
|
||||
-- log("num", num)
|
||||
-- log("bfnr", bufnr)
|
||||
@ -89,11 +79,11 @@ local ref_view = function(err, locations, ctx, cfg)
|
||||
local thread_items = vim.deepcopy(items)
|
||||
log('splits: ', #items, #second_part)
|
||||
|
||||
local ft = vim.api.nvim_buf_get_option(ctx.bufnr, 'ft')
|
||||
local ft = vim.api.nvim_buf_get_option(ctx.bufnr or 0, 'ft')
|
||||
|
||||
local wwidth = vim.api.nvim_get_option('columns')
|
||||
local mwidth = _NgConfigValues.width
|
||||
width = math.min(width + 30, 120, math.floor(wwidth * mwidth))
|
||||
width = math.min(width + 30, math.floor(wwidth * mwidth))
|
||||
-- log(items)
|
||||
-- log(width)
|
||||
opts = {
|
||||
@ -105,12 +95,22 @@ local ref_view = function(err, locations, ctx, cfg)
|
||||
api = 'Reference',
|
||||
enable_preview_edit = true,
|
||||
}
|
||||
local listview = gui.new_list_view(opts)
|
||||
local listview
|
||||
if not ctx.no_show then
|
||||
listview = gui.new_list_view(opts)
|
||||
|
||||
if listview == nil then
|
||||
vim.notify('failed to create preview windows', vim.lsp.log_levels.INFO)
|
||||
return
|
||||
if listview == nil then
|
||||
vim.notify('failed to create preview windows', vim.lsp.log_levels.INFO)
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
if ctx.no_show then
|
||||
opts.side_panel = true
|
||||
local data = require('navigator.render').prepare_for_render(items, opts)
|
||||
return data
|
||||
end
|
||||
|
||||
-- trace("update items", listview.ctrl.class)
|
||||
local nv_ref_async
|
||||
nv_ref_async = vim.loop.new_async(vim.schedule_wrap(function()
|
||||
@ -145,6 +145,9 @@ end
|
||||
local ref_hdlr = function(err, locations, ctx, cfg)
|
||||
_NgConfigValues.closer = nil
|
||||
trace(err, locations, ctx, cfg)
|
||||
if ctx.no_show then
|
||||
return ref_view(err, locations, ctx, cfg)
|
||||
end
|
||||
M.async_hdlr = vim.loop.new_async(vim.schedule_wrap(function()
|
||||
ref_view(err, locations, ctx, cfg)
|
||||
if M.async_hdlr:is_active() then
|
||||
@ -219,7 +222,36 @@ local ref = function()
|
||||
end)
|
||||
end
|
||||
|
||||
local function side_panel()
|
||||
local Panel = require('guihua.panel')
|
||||
|
||||
local currentWord = vim.fn.expand('<cword>')
|
||||
local p = Panel:new({
|
||||
scope = 'range',
|
||||
header = ' ' .. currentWord .. ' ref ',
|
||||
render = function(bufnr)
|
||||
local ft = vim.api.nvim_buf_get_option(bufnr, 'buftype')
|
||||
if ft == 'nofile' or ft == 'guihua' or ft == 'prompt' then
|
||||
return
|
||||
end
|
||||
local ref_params = vim.lsp.util.make_position_params()
|
||||
local sync_req = require('navigator.lspwrapper').call_sync
|
||||
return sync_req(
|
||||
'textDocument/references',
|
||||
ref_params,
|
||||
{ timeout = 1000, bufnr = bufnr, no_show = true },
|
||||
vim.lsp.with(function(err, locations, ctx, cfg)
|
||||
cfg.side_panel = true
|
||||
return ref_hdlr(err, locations, ctx, cfg)
|
||||
end, { no_show = true })
|
||||
)
|
||||
end,
|
||||
})
|
||||
p:open(true)
|
||||
end
|
||||
|
||||
return {
|
||||
side_panel = side_panel,
|
||||
reference_handler = ref_hdlr,
|
||||
reference = ref_req,
|
||||
ref_view = ref_view,
|
||||
|
@ -1,7 +1,9 @@
|
||||
local log = require('guihua.log').info
|
||||
local trace = require('guihua.log').trace
|
||||
local M = {}
|
||||
local util = require('navigator.util')
|
||||
local log = util.log
|
||||
local trace = util.trace
|
||||
local clone = require('guihua.util').clone
|
||||
|
||||
local M = {}
|
||||
local function filename(url)
|
||||
if url == nil then
|
||||
return ''
|
||||
@ -69,7 +71,7 @@ function M.prepare_for_render(items, opts)
|
||||
icon = devicons.get_icon(fn, ext) or icon
|
||||
end
|
||||
-- local call_by_presented = false
|
||||
opts.width = opts.width or 100
|
||||
opts.width = opts.width or math.floor(vim.api.nvim_get_option('columns') * 0.8)
|
||||
local win_width = opts.width -- buf
|
||||
|
||||
for i = 1, #items do
|
||||
@ -150,52 +152,28 @@ function M.prepare_for_render(items, opts)
|
||||
trace(ts_report, header_len)
|
||||
|
||||
item.text = item.text:gsub('%s*[%[%(%{]*%s*$', '')
|
||||
if item.call_by ~= nil and #item.call_by > 0 then
|
||||
trace('call_by:', #item.call_by)
|
||||
for _, value in pairs(item.call_by) do
|
||||
if value.node_text then
|
||||
local txt = value.node_text:gsub('%s*[%[%(%{]*%s*$', '')
|
||||
local endwise = '{}'
|
||||
if value.type == 'method' or value.type == 'function' then
|
||||
endwise = '()'
|
||||
local syb = items[i].symbol_name
|
||||
if txt == items[i].symbol_name or (#txt > #syb and txt:sub(#txt - #syb + 1) == syb) then
|
||||
if ts_report ~= _NgConfigValues.icons.value_definition .. ' ' then
|
||||
ts_report = ts_report .. _NgConfigValues.icons.value_definition .. ' '
|
||||
end
|
||||
header_len = #ts_report + 1
|
||||
else
|
||||
ts_report = ts_report .. ' '
|
||||
end
|
||||
end
|
||||
if #ts_report > header_len then
|
||||
ts_report = ts_report .. ' '
|
||||
end
|
||||
ts_report = ts_report .. value.kind .. txt .. endwise
|
||||
trace(item)
|
||||
end
|
||||
end
|
||||
if item.call_by ~= nil and item.call_by ~= '' then
|
||||
ts_report = ts_report .. ' ' .. item.call_by
|
||||
end
|
||||
if #ts_report > 1 then
|
||||
space, trim = get_pads(win_width, item.text, ts_report)
|
||||
|
||||
local l = math.max(20, opts.width - math.min(20, #ts_report))
|
||||
if trim and #item.text < l then
|
||||
trim = false
|
||||
end
|
||||
if trim then
|
||||
local ts_r = ts_report or ''
|
||||
item.text = string.sub(item.text, 1, math.max(1, opts.width - math.max(20, #ts_r)))
|
||||
local _, j = string.gsub(item.text, [["]], '')
|
||||
if j % 2 == 1 then
|
||||
item.text = item.text .. '"'
|
||||
end
|
||||
_, j = string.gsub(item.text, [[']], '')
|
||||
if j % 2 == 1 then
|
||||
item.text = item.text .. [[']]
|
||||
end
|
||||
item.text = item.text .. ''
|
||||
item.text = string.sub(item.text, 1, l)
|
||||
item.text = util.sub_match(item.text)
|
||||
-- let check if there are unmatched "/'
|
||||
end
|
||||
if #space + #item.text + #ts_report >= win_width then
|
||||
if #item.text + #ts_report > win_width then
|
||||
trace('exceeding', #item.text, #ts_report, win_width)
|
||||
space = ' '
|
||||
if #item.text + #ts_report >= win_width then
|
||||
space = ' '
|
||||
local len = math.max(win_width - #item.text - 4, 16)
|
||||
|
||||
trace('exceeding', #item.text, #ts_report, win_width, len)
|
||||
ts_report = ts_report:sub(1, len)
|
||||
else
|
||||
local remain = win_width - #item.text - #ts_report
|
||||
trace('remain', remain)
|
||||
|
@ -23,6 +23,7 @@ local cwd = vim.loop.cwd()
|
||||
local log = require('navigator.util').log
|
||||
local lerr = require('navigator.util').error
|
||||
local trace = function(...) end
|
||||
trace = log
|
||||
if vim.fn.has('nvim-0.7') == 1 then
|
||||
local trace = require('navigator.util').trace
|
||||
end
|
||||
@ -109,6 +110,96 @@ function M.find_definition(range, bufnr)
|
||||
end
|
||||
end
|
||||
|
||||
function M.get_tsnode_at_pos(pos, bufnr, ignore_injected_langs)
|
||||
if not pos or not pos.start then
|
||||
return
|
||||
end
|
||||
local cursor_range = { pos.start.line, pos.start.character }
|
||||
|
||||
local buf = bufnr
|
||||
local root_lang_tree = parsers.get_parser(buf)
|
||||
if not root_lang_tree then
|
||||
return
|
||||
end
|
||||
|
||||
local root
|
||||
if ignore_injected_langs then
|
||||
for _, tree in ipairs(root_lang_tree:trees()) do
|
||||
local tree_root = tree:root()
|
||||
if tree_root and ts_utils.is_in_node_range(tree_root, cursor_range[1], cursor_range[2]) then
|
||||
root = tree_root
|
||||
break
|
||||
end
|
||||
end
|
||||
else
|
||||
root = ts_utils.get_root_for_position(cursor_range[1], cursor_range[2], root_lang_tree)
|
||||
end
|
||||
|
||||
if not root then
|
||||
return
|
||||
end
|
||||
|
||||
return root:named_descendant_for_range(cursor_range[1], cursor_range[2], cursor_range[1], cursor_range[2])
|
||||
end
|
||||
|
||||
-- Trim spaces and opening brackets from end
|
||||
local transform_line = function(line)
|
||||
line = line:gsub("%s*[%[%(%{]*%s*$", "")
|
||||
line = line:gsub("function", "")
|
||||
line = line:gsub("func%w*%s+", "")
|
||||
if _NgConfigValues.treesitter_analysis_condense then
|
||||
line = line:gsub("%([%a%.,%s%[%]%*]+%)", "()")
|
||||
-- this is for multi return
|
||||
line = line:gsub("%([%a%.,%s%[%]%*]+%)", "()")
|
||||
line = line:gsub("%(%)%s*%(%)", "()")
|
||||
end
|
||||
return line
|
||||
end
|
||||
|
||||
function M.ref_context(opts)
|
||||
if not parsers.has_parser() then
|
||||
return
|
||||
end
|
||||
local options = opts or {}
|
||||
|
||||
local bufnr = options.bufnr or 0
|
||||
local pos = options.pos
|
||||
if not pos then
|
||||
pos = {start = vim.lsp.util.make_position_params().position}
|
||||
end
|
||||
local indicator_size = options.indicator_size or 100
|
||||
local type_patterns = options.type_patterns or { "class", "function", "method" }
|
||||
local transform_fn = options.transform_fn or transform_line
|
||||
local separator = options.separator or " "
|
||||
|
||||
local current_node = M.get_tsnode_at_pos(pos, bufnr)
|
||||
if not current_node then
|
||||
log('no node at pos', bufnr, pos)
|
||||
return ""
|
||||
end
|
||||
|
||||
local lines = {}
|
||||
local expr = current_node
|
||||
|
||||
while expr do
|
||||
local line = ts_utils._get_line_for_node(expr, type_patterns, transform_fn, bufnr)
|
||||
log(line)
|
||||
if line ~= "" and not vim.tbl_contains(lines, line) then
|
||||
table.insert(lines, 1, line)
|
||||
end
|
||||
expr = expr:parent()
|
||||
end
|
||||
|
||||
local text = table.concat(lines, separator)
|
||||
local text_len = #text
|
||||
if text_len > indicator_size then
|
||||
local str = text:sub(1, text_len)
|
||||
return util.sub_match(str)
|
||||
end
|
||||
|
||||
return text
|
||||
end
|
||||
|
||||
--- Get definitions of bufnr (unique and sorted by order of appearance).
|
||||
--- This function copy from treesitter/refactor/navigation.lua
|
||||
local function get_definitions(bufnr)
|
||||
@ -121,23 +212,23 @@ local function get_definitions(bufnr)
|
||||
ts_locals.recurse_local_nodes(loc.definition, function(_, node, _, match)
|
||||
-- lua doesn't compare tables by value,
|
||||
-- use the value from byte count instead.
|
||||
local k, l, start = node:start()
|
||||
local row, col, offset = node:start()
|
||||
local erow, ecol, end_ = node:end_()
|
||||
trace(node, match)
|
||||
trace(k, l, start, node:parent(), node:parent():start(), node:parent():type())
|
||||
trace(row, col, erow, offset, node:parent(), node:parent():start(), node:parent():type())
|
||||
|
||||
if node and node:parent() and string.find(node:parent():type(), 'parameter_declaration') then
|
||||
log('parameter_declaration skip')
|
||||
return
|
||||
end
|
||||
nodes_set[start] = { node = node, type = match or '' }
|
||||
nodes_set[offset] = { node = node, type = match or '' }
|
||||
end)
|
||||
end
|
||||
|
||||
if loc.method then -- for go
|
||||
ts_locals.recurse_local_nodes(loc.method, function(def, node, full_match, match)
|
||||
local k, l, start = node:start()
|
||||
|
||||
trace(k, l, start, def, node, full_match, match, node:parent(), node:parent():start(), node:parent():type())
|
||||
local row, col, start = node:start()
|
||||
trace(row, col, start, def, node, full_match, match, node:parent(), node:parent():start(), node:parent():type())
|
||||
if node:type() == 'field_identifier' and nodes_set[start] == nil then
|
||||
nodes_set[start] = { node = node, type = 'method' }
|
||||
end
|
||||
@ -154,16 +245,32 @@ local function get_definitions(bufnr)
|
||||
end
|
||||
if loc.reference then -- for go
|
||||
ts_locals.recurse_local_nodes(loc.reference, function(def, node, full_match, match)
|
||||
local k, l, start = node:start()
|
||||
local row, col, start = node:start()
|
||||
local p1, p1t = '', ''
|
||||
local p2, p2t = '', ''
|
||||
local p3, p3t = '', ''
|
||||
if node:parent() and node:parent():parent() then
|
||||
p1 = node:parent()
|
||||
p1t = node:parent():type()
|
||||
p2 = node:parent():parent()
|
||||
p2t = node:parent():parent():type()
|
||||
end
|
||||
trace(k, l, start, def, node, full_match, match, p1t, p1, node:parent():start(), node:parent():type(), p2, p2t)
|
||||
if p2 and p2:parent() then
|
||||
p3 = p2:parent()
|
||||
p3t = p2:parent():type()
|
||||
end
|
||||
trace(row, col, start, def, node, full_match, match, p1t, p1, node:parent():start(), node:parent():type(), p2, p2t, p3, p3t)
|
||||
if p1t == 'arrow_function' then
|
||||
row, col, start = p1:start()
|
||||
trace('arrow_function 1', row, col)
|
||||
nodes_set[start] = { node = p1, type = p1t }
|
||||
end
|
||||
|
||||
if p2t == 'arrow_function' then
|
||||
row, col, start = p2:start()
|
||||
trace('arrow_function 2', row, col)
|
||||
nodes_set[start] = { node = p2, type = p2t }
|
||||
end
|
||||
if nodes_set[start] == nil then
|
||||
if -- qualified_type : e.g. io.Reader inside interface
|
||||
node:parent()
|
||||
@ -210,7 +317,7 @@ local function get_scope(type, source)
|
||||
local parent = current:parent()
|
||||
trace(source:type(), source:range(), parent)
|
||||
|
||||
if type == 'method' or type == 'function' and parent ~= nil then
|
||||
if type == 'method' or type:find('function') and parent ~= nil then
|
||||
trace(parent:type(), parent:range())
|
||||
-- a function name
|
||||
if parent:type() == 'function_name' then
|
||||
@ -345,7 +452,7 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
|
||||
trace(bufnr, filter, summary)
|
||||
if not bufnr then
|
||||
vim.notify('get_all_node invalide bufnr', vim.lsp.log_levels.WARN)
|
||||
vim.notify('get_all_node invalid bufnr', vim.lsp.log_levels.WARN)
|
||||
end
|
||||
summary = summary or false
|
||||
local ft = vim.api.nvim_buf_get_option(bufnr, 'filetype')
|
||||
@ -362,17 +469,13 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
local display_filename = fname:gsub(cwd .. path_sep, path_cur, 1)
|
||||
|
||||
local all_nodes = {}
|
||||
-- Support completion-nvim customized label map
|
||||
-- local customized_labels = vim.g.completion_customize_lsp_label or {}
|
||||
|
||||
-- Force some types to act like they are parents
|
||||
-- instead of neighbors of the next nodes.
|
||||
local containers = {
|
||||
local containers = filter or {
|
||||
['function'] = true,
|
||||
['local_function'] = true,
|
||||
['arrow_function'] = true,
|
||||
['type'] = true,
|
||||
['class'] = true,
|
||||
['call_expression'] = true,
|
||||
-- ['var'] = true,
|
||||
['struct'] = true,
|
||||
['method'] = true,
|
||||
@ -395,8 +498,8 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
for i = 1, n do
|
||||
local index = n + 1 - i
|
||||
local parent_def = parents[index]
|
||||
log(parent_def.type, parent_def.node:type(), vim.treesitter.get_node_text(parent_def.node, bufnr))
|
||||
log(def.node:type(), vim.treesitter.get_node_text(def.node, bufnr))
|
||||
-- trace(parent_def.type, parent_def.node:type(), vim.treesitter.get_node_text(parent_def.node, bufnr))
|
||||
-- trace(def.node:type(), vim.treesitter.get_node_text(def.node, bufnr))
|
||||
if
|
||||
ts_utils.is_parent(parent_def.node, def.node)
|
||||
or (
|
||||
@ -410,10 +513,10 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
)
|
||||
)
|
||||
then
|
||||
log('is parent', i, index)
|
||||
-- trace('is parent', i, index)
|
||||
break
|
||||
else
|
||||
log('leave node', i, index)
|
||||
-- trace('leave node', i, index)
|
||||
parents[index] = nil
|
||||
end
|
||||
end
|
||||
@ -440,7 +543,10 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
trace('skipped', item.type, item.kind)
|
||||
goto continue
|
||||
end
|
||||
item.node_text = vim.treesitter.get_node_text(tsdata, bufnr) or ''
|
||||
local text = vim.treesitter.get_node_text(tsdata, bufnr) or ''
|
||||
text = vim.split(text, '\n')[1] or ''
|
||||
item.node_text = text
|
||||
log(item.node_text)
|
||||
local scope, is_func
|
||||
|
||||
if summary then
|
||||
@ -448,6 +554,7 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
else
|
||||
scope, is_func = get_smallest_context(tsdata)
|
||||
end
|
||||
log(item, scope, is_func)
|
||||
if is_func then
|
||||
-- hack for lua and maybe other language aswell
|
||||
local parent = tsdata:parent()
|
||||
@ -477,7 +584,7 @@ local function get_all_nodes(bufnr, filter, summary)
|
||||
trace(item.node_text, item.kind, item.type)
|
||||
if scope ~= nil then
|
||||
if not is_func and summary then
|
||||
log('skipped', item.node_text, item.type)
|
||||
trace('skipped', item.node_text, item.type)
|
||||
goto continue
|
||||
end
|
||||
item.node_scope = ts_utils.node_to_lsp_range(scope)
|
||||
@ -581,6 +688,7 @@ function M.buf_func(bufnr)
|
||||
|
||||
local all_nodes, width = get_all_nodes(bufnr, {
|
||||
['function'] = true,
|
||||
['arrow_function'] = true,
|
||||
['var'] = true,
|
||||
['method'] = true,
|
||||
['class'] = true,
|
||||
@ -614,6 +722,7 @@ function M.buf_func(bufnr)
|
||||
return false
|
||||
end)
|
||||
end
|
||||
log(all_nodes)
|
||||
|
||||
return all_nodes, width
|
||||
end
|
||||
|
@ -61,7 +61,7 @@ function M.get_data_from_file(filename, startLine)
|
||||
return { data = data, line = displayLine }
|
||||
end
|
||||
|
||||
function M.io_read(filename, total)
|
||||
function M.io_read(filename)
|
||||
local f = io.open(filename, 'r')
|
||||
if f == nil then
|
||||
return nil
|
||||
@ -504,7 +504,7 @@ function M.dedup(locations)
|
||||
if not range then
|
||||
break
|
||||
end
|
||||
local key = (range.uri or value.targetUri or '')
|
||||
local key = (value.uri or range.uri or value.targetUri or '')
|
||||
.. ':'
|
||||
.. tostring(range.start.line)
|
||||
.. ':'
|
||||
@ -524,7 +524,9 @@ function M.dedup(locations)
|
||||
end
|
||||
end
|
||||
end
|
||||
table.sort(del)
|
||||
for i = #del, 1, -1 do
|
||||
M.log('remove ', del[i])
|
||||
table.remove(locations, del[i])
|
||||
end
|
||||
return locations
|
||||
@ -540,4 +542,31 @@ function M.range_inside(outer, inner)
|
||||
return outer.start.line <= inner.start.line and outer['end'].line >= inner['end'].line
|
||||
end
|
||||
|
||||
function M.dirname(pathname)
|
||||
local path_sep = require('navigator.util').path_sep()
|
||||
local strip_dir_pat = path_sep .. '([^' .. path_sep .. ']+)$'
|
||||
local strip_sep_pat = path_sep .. '$'
|
||||
if not pathname or #pathname == 0 then
|
||||
return
|
||||
end
|
||||
local result = pathname:gsub(strip_sep_pat, ''):gsub(strip_dir_pat, '')
|
||||
if #result == 0 then
|
||||
return '/'
|
||||
end
|
||||
return result
|
||||
end
|
||||
|
||||
function M.sub_match(str)
|
||||
local _, j = string.gsub(str, [["]], '')
|
||||
if j % 2 == 1 then
|
||||
str = str .. '"'
|
||||
end
|
||||
_, j = string.gsub(str, [[']], '')
|
||||
if j % 2 == 1 then
|
||||
str = str .. [[']]
|
||||
end
|
||||
str = str .. ''
|
||||
return str
|
||||
end
|
||||
|
||||
return M
|
||||
|
@ -19,7 +19,7 @@ M.remove_workspace_folder = function()
|
||||
local folders = vim.lsp.buf.list_workspace_folders()
|
||||
|
||||
if #folders > 1 then
|
||||
select(folders, { prompt = 'select workspace to delete' }, function(workspace)
|
||||
return select(folders, { prompt = 'select workspace to delete' }, function(workspace)
|
||||
vim.lsp.buf.remove_workspace_folder(workspace)
|
||||
end)
|
||||
end
|
||||
@ -37,7 +37,7 @@ function M.workspace_symbol_live()
|
||||
local height = _NgConfigValues.height or 0.4
|
||||
height = math.floor(height * vfn.winheight('%'))
|
||||
local width = _NgConfigValues.width or 0.7
|
||||
width = math.floor(width * vfn.winwidth('%'))
|
||||
width = math.floor(vim.api.nvim_get_option('columns') * width)
|
||||
local bufnr = vim.api.nvim_get_current_buf()
|
||||
local ft = vim.o.ft
|
||||
local data = { { text = 'input the symbol name to start fuzzy search' } }
|
||||
@ -47,7 +47,7 @@ function M.workspace_symbol_live()
|
||||
local ListView = require('guihua.listview')
|
||||
local opt = {
|
||||
api = ' ',
|
||||
bg = 'GHListDark',
|
||||
bg = 'GuihuaListDark',
|
||||
data = data,
|
||||
items = data,
|
||||
enter = true,
|
||||
|
@ -1 +1,6 @@
|
||||
std="lua51+vim"
|
||||
std="lua52+vim"
|
||||
|
||||
[rules]
|
||||
global_usage = "allow"
|
||||
multiple_statements = "allow"
|
||||
unused_variable = "allow"
|
||||
|
@ -60,10 +60,10 @@ describe('should run lsp call hierarchy', function()
|
||||
-- eq(panel.activePanel.sections[1].nodes[1].name, 'measure')
|
||||
end)
|
||||
|
||||
it('should show hierarchy', function()
|
||||
it('should not crash and show hierarchy', function()
|
||||
vim.fn.setpos('.', { bufn, 24, 15, 0 })
|
||||
local ret = require('navigator.hierarchy')._call_hierarchy()
|
||||
vim.wait(400, function() end)
|
||||
eq(ret, {})
|
||||
eq(ret, ret) -- make sure doesn't crash the result
|
||||
end)
|
||||
end)
|
||||
|
@ -114,9 +114,9 @@ describe('should run lsp reference', function()
|
||||
|
||||
-- print('win', vim.inspect(win))
|
||||
print('items', vim.inspect(items))
|
||||
eq(win.ctrl.data[1].display_filename, './interface.go')
|
||||
eq(win.ctrl.data[1].display_filename, './tests/fixtures/interface.go')
|
||||
eq(win.ctrl.data[2].range.start.line, 14)
|
||||
eq(items[1].display_filename, './interface.go')
|
||||
eq(items[1].display_filename, './tests/fixtures/interface.go')
|
||||
|
||||
-- eq(width, 60)
|
||||
end)
|
||||
@ -137,7 +137,7 @@ describe('should run lsp reference', function()
|
||||
-- print('win', vim.inspect(win))
|
||||
print('items', vim.inspect(items))
|
||||
-- eq(win.ctrl.data, "./interface.go")
|
||||
eq(win.ctrl.data[1].display_filename, './interface.go')
|
||||
eq(win.ctrl.data[1].display_filename, './tests/fixtures/interface.go')
|
||||
eq(win.ctrl.data[2].range.start.line, 14)
|
||||
-- eq(items[1].display_filename, "./interface.go")
|
||||
|
||||
|
8
vim.toml
8
vim.toml
@ -1,5 +1,5 @@
|
||||
[selene]
|
||||
base = "lua51"
|
||||
base = "lua52"
|
||||
name = "vim"
|
||||
|
||||
[vim]
|
||||
@ -8,9 +8,11 @@ any = true
|
||||
[_G]
|
||||
property = true
|
||||
writable = "new-fields"
|
||||
|
||||
[_NgConfigValues]
|
||||
property = true
|
||||
writable = "new-fields"
|
||||
any = true
|
||||
# property = true
|
||||
# writable = "full-write"
|
||||
|
||||
[debug]
|
||||
property = true
|
||||
|
47
vim.yml
Normal file
47
vim.yml
Normal file
@ -0,0 +1,47 @@
|
||||
---
|
||||
base: lua52
|
||||
name: vim
|
||||
globals:
|
||||
_G:
|
||||
property: new-fields
|
||||
_NgConfigValues:
|
||||
any: true
|
||||
after_each:
|
||||
args:
|
||||
- type: function
|
||||
assert.equals:
|
||||
args:
|
||||
- type: any
|
||||
- type: any
|
||||
- required: false
|
||||
type: any
|
||||
assert.is_not:
|
||||
any: true
|
||||
assert.same:
|
||||
args:
|
||||
- type: any
|
||||
- type: any
|
||||
assert.spy:
|
||||
args:
|
||||
- type: any
|
||||
assert.stub:
|
||||
args:
|
||||
- type: any
|
||||
assert.truthy:
|
||||
args:
|
||||
- type: any
|
||||
before_each:
|
||||
args:
|
||||
- type: function
|
||||
debug:
|
||||
property: read-only
|
||||
describe:
|
||||
args:
|
||||
- type: string
|
||||
- type: function
|
||||
it:
|
||||
args:
|
||||
- type: string
|
||||
- type: function
|
||||
vim:
|
||||
any: true
|
Loading…
Reference in New Issue
Block a user