diff --git a/autoload/ale/definition.vim b/autoload/ale/definition.vim index 984a4f9d..79d12596 100644 --- a/autoload/ale/definition.vim +++ b/autoload/ale/definition.vim @@ -86,7 +86,7 @@ function! s:OnReady(linter, lsp_details, line, column, options, ...) abort let l:request_id = ale#lsp#Send(l:id, l:message) let s:go_to_definition_map[l:request_id] = { - \ 'open_in_tab': get(a:options, 'open_in_tab', 0), + \ 'open_in': get(a:options, 'open_in', 'current-buffer'), \} endfunction diff --git a/autoload/ale/util.vim b/autoload/ale/util.vim index bb478957..ee9359f8 100644 --- a/autoload/ale/util.vim +++ b/autoload/ale/util.vim @@ -87,12 +87,25 @@ function! ale#util#GetFunction(string_or_ref) abort return a:string_or_ref endfunction +" Open the file (at the given line). +" options['open_in'] can be: +" current-buffer (default) +" tab +" vertical-split +" horizontal-split function! ale#util#Open(filename, line, column, options) abort - if get(a:options, 'open_in_tab', 0) - call ale#util#Execute('tabedit +' . a:line . ' ' . fnameescape(a:filename)) + let l:open_in = get(a:options, 'open_in', 'current-buffer') + let l:args_to_open = '+' . a:line . ' ' . fnameescape(a:filename) + + if l:open_in is# 'tab' + call ale#util#Execute('tabedit ' . l:args_to_open) + elseif l:open_in is# 'horizontal-split' + call ale#util#Execute('split ' . l:args_to_open) + elseif l:open_in is# 'vertical-split' + call ale#util#Execute('vsplit ' . l:args_to_open) elseif bufnr(a:filename) isnot bufnr('') " Open another file only if we need to. - call ale#util#Execute('edit +' . a:line . ' ' . fnameescape(a:filename)) + call ale#util#Execute('edit ' . l:args_to_open) else normal! m` endif diff --git a/doc/ale.txt b/doc/ale.txt index 0b127725..e5951745 100644 --- a/doc/ale.txt +++ b/doc/ale.txt @@ -836,6 +836,8 @@ information returned by LSP servers. The following commands are supported: |ALEGoToDefinition| - Open the definition of the symbol under the cursor. |ALEGoToDefinitionInTab| - The same, but for opening the file in a new tab. +|ALEGoToDefinitionInSplit| - The same, but in a new split. +|ALEGoToDefinitionInVSplit| - The same, but in a new vertical split. ------------------------------------------------------------------------------- @@ -2262,6 +2264,22 @@ ALEGoToDefinitionInTab *ALEGoToDefinitionInTab* command. +ALEGoToDefinitionInSplit *ALEGoToDefinitionInSplit* + + The same as |ALEGoToDefinition|, but opens results in a new split. + + A plug mapping `(ale_go_to_definition_in_split)` is defined for this + command. + + +ALEGoToDefinitionInVSplit *ALEGoToDefinitionInVSplit* + + The same as |ALEGoToDefinition|, but opens results in a new vertical split. + + A plug mapping `(ale_go_to_definition_in_vsplit)` is defined for this + command. + + ALEHover *ALEHover* Print brief information about the symbol under the cursor, taken from any diff --git a/plugin/ale.vim b/plugin/ale.vim index 610ff142..f57a495c 100644 --- a/plugin/ale.vim +++ b/plugin/ale.vim @@ -188,7 +188,9 @@ command! -bar ALEFixSuggest :call ale#fix#registry#Suggest(&filetype) " Go to definition for tsserver and LSP command! -bar ALEGoToDefinition :call ale#definition#GoTo({}) -command! -bar ALEGoToDefinitionInTab :call ale#definition#GoTo({'open_in_tab': 1}) +command! -bar ALEGoToDefinitionInTab :call ale#definition#GoTo({'open_in': 'tab'}) +command! -bar ALEGoToDefinitionInSplit :call ale#definition#GoTo({'open_in': 'horizontal-split'}) +command! -bar ALEGoToDefinitionInVSplit :call ale#definition#GoTo({'open_in': 'vertical-split'}) " Find references for tsserver and LSP command! -bar ALEFindReferences :call ale#references#Find() @@ -222,6 +224,8 @@ nnoremap (ale_detail) :ALEDetail nnoremap (ale_fix) :ALEFix nnoremap (ale_go_to_definition) :ALEGoToDefinition nnoremap (ale_go_to_definition_in_tab) :ALEGoToDefinitionInTab +nnoremap (ale_go_to_definition_in_split) :ALEGoToDefinitionInSplit +nnoremap (ale_go_to_definition_in_vsplit) :ALEGoToDefinitionInVSplit nnoremap (ale_find_references) :ALEFindReferences nnoremap (ale_hover) :ALEHover nnoremap (ale_documentation) :ALEDocumentation diff --git a/test/test_go_to_definition.vader b/test/test_go_to_definition.vader index 66c24fb6..4e4e2552 100644 --- a/test/test_go_to_definition.vader +++ b/test/test_go_to_definition.vader @@ -71,7 +71,7 @@ Execute(Other messages for the tsserver handler should be ignored): call ale#definition#HandleTSServerResponse(1, {'command': 'foo'}) Execute(Failed definition responses should be handled correctly): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleTSServerResponse( \ 1, \ {'command': 'definition', 'request_seq': 3} @@ -79,7 +79,7 @@ Execute(Failed definition responses should be handled correctly): AssertEqual {}, ale#definition#GetMap() Execute(Failed definition responses with no files should be handled correctly): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleTSServerResponse( \ 1, \ { @@ -97,7 +97,7 @@ Given typescript(Some typescript file): bazxyzxyzxyz Execute(Other files should be jumped to for definition responses): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleTSServerResponse( \ 1, \ { @@ -122,7 +122,7 @@ Execute(Other files should be jumped to for definition responses): AssertEqual {}, ale#definition#GetMap() Execute(Other files should be jumped to for definition responses in tabs too): - call ale#definition#SetMap({3: {'open_in_tab': 1}}) + call ale#definition#SetMap({3: {'open_in': 'tab'}}) call ale#definition#HandleTSServerResponse( \ 1, \ { @@ -146,6 +146,56 @@ Execute(Other files should be jumped to for definition responses in tabs too): AssertEqual [3, 7], getpos('.')[1:2] AssertEqual {}, ale#definition#GetMap() +Execute(Other files should be jumped to for definition responses in splits too): + call ale#definition#SetMap({3: {'open_in': 'horizontal-split'}}) + call ale#definition#HandleTSServerResponse( + \ 1, + \ { + \ 'command': 'definition', + \ 'request_seq': 3, + \ 'success': v:true, + \ 'body': [ + \ { + \ 'file': ale#path#Simplify(g:dir . '/completion_dummy_file'), + \ 'start': {'line': 3, 'offset': 7}, + \ }, + \ ], + \ } + \) + + AssertEqual + \ [ + \ 'split +3 ' . fnameescape(ale#path#Simplify(g:dir . '/completion_dummy_file')), + \ ], + \ g:expr_list + AssertEqual [3, 7], getpos('.')[1:2] + AssertEqual {}, ale#definition#GetMap() + +Execute(Other files should be jumped to for definition responses in vsplits too): + call ale#definition#SetMap({3: {'open_in': 'vertical-split'}}) + call ale#definition#HandleTSServerResponse( + \ 1, + \ { + \ 'command': 'definition', + \ 'request_seq': 3, + \ 'success': v:true, + \ 'body': [ + \ { + \ 'file': ale#path#Simplify(g:dir . '/completion_dummy_file'), + \ 'start': {'line': 3, 'offset': 7}, + \ }, + \ ], + \ } + \) + + AssertEqual + \ [ + \ 'vsplit +3 ' . fnameescape(ale#path#Simplify(g:dir . '/completion_dummy_file')), + \ ], + \ g:expr_list + AssertEqual [3, 7], getpos('.')[1:2] + AssertEqual {}, ale#definition#GetMap() + Execute(tsserver completion requests should be sent): runtime ale_linters/typescript/tsserver.vim call setpos('.', [bufnr(''), 2, 5, 0]) @@ -165,7 +215,7 @@ Execute(tsserver completion requests should be sent): AssertEqual \ [[0, 'ts@definition', {'file': expand('%:p'), 'line': 2, 'offset': 5}]], \ g:message_list - AssertEqual {'42': {'open_in_tab': 0}}, ale#definition#GetMap() + AssertEqual {'42': {'open_in': 'current-buffer'}}, ale#definition#GetMap() Execute(tsserver tab completion requests should be sent): runtime ale_linters/typescript/tsserver.vim @@ -186,7 +236,7 @@ Execute(tsserver tab completion requests should be sent): AssertEqual \ [[0, 'ts@definition', {'file': expand('%:p'), 'line': 2, 'offset': 5}]], \ g:message_list - AssertEqual {'42': {'open_in_tab': 1}}, ale#definition#GetMap() + AssertEqual {'42': {'open_in': 'tab'}}, ale#definition#GetMap() Given python(Some Python file): foo @@ -194,7 +244,7 @@ Given python(Some Python file): bazxyzxyzxyz Execute(Other files should be jumped to for LSP definition responses): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleLSPResponse( \ 1, \ { @@ -217,7 +267,7 @@ Execute(Other files should be jumped to for LSP definition responses): AssertEqual {}, ale#definition#GetMap() Execute(Locations inside the same file should be jumped to without using :edit): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleLSPResponse( \ 1, \ { @@ -239,7 +289,7 @@ Execute(Locations inside the same file should be jumped to without using :edit): AssertEqual {}, ale#definition#GetMap() Execute(Other files should be jumped to in tabs for LSP definition responses): - call ale#definition#SetMap({3: {'open_in_tab': 1}}) + call ale#definition#SetMap({3: {'open_in': 'tab'}}) call ale#definition#HandleLSPResponse( \ 1, \ { @@ -262,7 +312,7 @@ Execute(Other files should be jumped to in tabs for LSP definition responses): AssertEqual {}, ale#definition#GetMap() Execute(Definition responses with lists should be handled): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleLSPResponse( \ 1, \ { @@ -293,7 +343,7 @@ Execute(Definition responses with lists should be handled): AssertEqual {}, ale#definition#GetMap() Execute(Definition responses with null response should be handled): - call ale#definition#SetMap({3: {'open_in_tab': 0}}) + call ale#definition#SetMap({3: {'open_in': 'current-buffer'}}) call ale#definition#HandleLSPResponse(1, {'id': 3, 'result': v:null}) AssertEqual [], g:expr_list @@ -332,7 +382,7 @@ Execute(LSP completion requests should be sent): \ ], \ g:message_list - AssertEqual {'42': {'open_in_tab': 0}}, ale#definition#GetMap() + AssertEqual {'42': {'open_in': 'current-buffer'}}, ale#definition#GetMap() Execute(LSP tab completion requests should be sent): runtime ale_linters/python/pyls.vim @@ -368,4 +418,4 @@ Execute(LSP tab completion requests should be sent): \ ], \ g:message_list - AssertEqual {'42': {'open_in_tab': 1}}, ale#definition#GetMap() + AssertEqual {'42': {'open_in': 'tab'}}, ale#definition#GetMap()