diff --git a/autoload/lsp/omni.vim b/autoload/lsp/omni.vim index d203f8ff..663691f4 100644 --- a/autoload/lsp/omni.vim +++ b/autoload/lsp/omni.vim @@ -311,44 +311,43 @@ function! lsp#omni#get_vim_completion_items(options) abort \ 'icase': 1, \ } let l:range = lsp#utils#text_edit#get_range(get(l:completion_item, 'textEdit', {})) + let l:complete_word = '' if has_key(l:completion_item, 'textEdit') && type(l:completion_item['textEdit']) == s:t_dict && !empty(l:range) && has_key(l:completion_item['textEdit'], 'newText') let l:text_edit_new_text = l:completion_item['textEdit']['newText'] if has_key(l:completion_item, 'filterText') && !empty(l:completion_item['filterText']) && matchstr(l:text_edit_new_text, '^' . l:refresh_pattern) ==# '' " Use filterText as word. - let l:vim_complete_item['word'] = l:completion_item['filterText'] + let l:complete_word = l:completion_item['filterText'] else " Use textEdit.newText as word. - let l:vim_complete_item['word'] = l:text_edit_new_text + let l:complete_word = l:text_edit_new_text endif - " Fix overlapped text if needed. let l:item_start_character = l:range['start']['character'] - if l:item_start_character < l:default_start_character - " Add already typed word. The typescript-language-server returns `[Symbol]` item for the line of `Hoo.|`. So we should add `.` (`.[Symbol]`) . - let l:overlap_text = strcharpart(l:current_line, l:item_start_character, l:default_start_character - l:item_start_character) - if stridx(l:vim_complete_item['word'], l:overlap_text) != 0 - let l:vim_complete_item['word'] = l:overlap_text . l:vim_complete_item['word'] - endif - endif let l:start_character = min([l:item_start_character, l:start_character]) let l:start_characters += [l:item_start_character] elseif has_key(l:completion_item, 'insertText') && !empty(l:completion_item['insertText']) - let l:vim_complete_item['word'] = l:completion_item['insertText'] + let l:complete_word = l:completion_item['insertText'] let l:start_characters += [l:default_start_character] else - let l:vim_complete_item['word'] = l:completion_item['label'] + let l:complete_word = l:completion_item['label'] let l:start_characters += [l:default_start_character] endif if l:expandable - let l:vim_complete_item['word'] = lsp#utils#make_valid_word(substitute(l:vim_complete_item['word'], '\$[0-9]\+\|\${\%(\\.\|[^}]\)\+}', '', 'g')) + let l:vim_complete_item['word'] = lsp#utils#make_valid_word(substitute(l:complete_word, '\$[0-9]\+\|\${\%(\\.\|[^}]\)\+}', '', 'g')) let l:vim_complete_item['abbr'] = l:completion_item['label'] . '~' else + let l:vim_complete_item['word'] = l:complete_word let l:vim_complete_item['abbr'] = l:completion_item['label'] endif if s:is_user_data_support - let l:vim_complete_item['user_data'] = s:create_user_data(l:completion_item, l:server_name, l:complete_position, l:start_characters[len(l:start_characters) - 1]) + let l:vim_complete_item['user_data'] = s:create_user_data( + \ l:completion_item, + \ l:server_name, + \ l:complete_position, + \ l:start_characters[-1], + \ l:complete_word) endif let l:vim_complete_items += [l:vim_complete_item] @@ -382,13 +381,14 @@ endfunction " " create item's user_data. " -function! s:create_user_data(completion_item, server_name, complete_position, start_character) abort +function! s:create_user_data(completion_item, server_name, complete_position, start_character, complete_word) abort let l:user_data_key = s:create_user_data_key(s:managed_user_data_key_base) let s:managed_user_data_map[l:user_data_key] = { \ 'complete_position': a:complete_position, \ 'server_name': a:server_name, \ 'completion_item': a:completion_item, \ 'start_character': a:start_character, + \ 'complete_word': a:complete_word, \ } let s:managed_user_data_key_base += 1 return l:user_data_key diff --git a/autoload/lsp/ui/vim/completion.vim b/autoload/lsp/ui/vim/completion.vim index 87206ac5..3cf00d93 100644 --- a/autoload/lsp/ui/vim/completion.vim +++ b/autoload/lsp/ui/vim/completion.vim @@ -50,12 +50,12 @@ function! s:on_complete_done() abort let s:context['done_line'] = getline('.') let s:context['done_line_nr'] = line('.') - let s:context['completed_item'] = copy(v:completed_item) let s:context['done_position'] = lsp#utils#position#vim_to_lsp('%', getpos('.')[1 : 2]) let s:context['complete_position'] = l:managed_user_data['complete_position'] let s:context['server_name'] = l:managed_user_data['server_name'] let s:context['completion_item'] = l:managed_user_data['completion_item'] let s:context['start_character'] = l:managed_user_data['start_character'] + let s:context['complete_word'] = l:managed_user_data['complete_word'] call feedkeys(printf("\=%d_on_complete_done_after()\", s:SID()), 'n') endfunction @@ -73,12 +73,12 @@ function! s:on_complete_done_after() abort let l:done_line = s:context['done_line'] let l:done_line_nr = s:context['done_line_nr'] - let l:completed_item = s:context['completed_item'] let l:done_position = s:context['done_position'] let l:complete_position = s:context['complete_position'] let l:server_name = s:context['server_name'] let l:completion_item = s:context['completion_item'] let l:start_character = s:context['start_character'] + let l:complete_word = s:context['complete_word'] " check the commit characters are or . if line('.') ==# l:done_line_nr && strlen(getline('.')) < strlen(l:done_line) @@ -95,7 +95,7 @@ function! s:on_complete_done_after() abort let l:completion_item = s:resolve_completion_item(l:completion_item, l:server_name) " clear completed string if need. - let l:is_expandable = s:is_expandable(l:done_line, l:done_position, l:complete_position, l:completion_item, l:completed_item) + let l:is_expandable = s:is_expandable(l:done_line, l:done_position, l:complete_position, l:completion_item, l:complete_word) if l:is_expandable call s:clear_auto_inserted_text(l:done_line, l:done_position, l:complete_position) endif @@ -162,7 +162,7 @@ endfunction " " is_expandable " -function! s:is_expandable(done_line, done_position, complete_position, completion_item, completed_item) abort +function! s:is_expandable(done_line, done_position, complete_position, completion_item, complete_word) abort if get(a:completion_item, 'textEdit', v:null) isnot# v:null let l:range = lsp#utils#text_edit#get_range(a:completion_item['textEdit']) if l:range['start']['line'] != l:range['end']['line'] @@ -177,7 +177,7 @@ function! s:is_expandable(done_line, done_position, complete_position, completio let l:text_edit_after = strcharpart(l:completed_line, l:range['end']['character'], strchars(l:completed_line) - l:range['end']['character']) return a:done_line !=# l:text_edit_before . s:trim_unmeaning_tabstop(a:completion_item['textEdit']['newText']) . l:text_edit_after endif - return s:get_completion_text(a:completion_item) !=# s:trim_unmeaning_tabstop(a:completed_item['word']) + return s:get_completion_text(a:completion_item) !=# s:trim_unmeaning_tabstop(a:complete_word) endfunction " @@ -246,7 +246,7 @@ endfunction function! s:clear_auto_inserted_text(done_line, done_position, complete_position) abort let l:before = strcharpart(a:done_line, 0, a:complete_position['character']) let l:after = strcharpart(a:done_line, a:done_position['character'], (strchars(a:done_line) - a:done_position['character'])) - call setline('.', l:before . l:after) + call setline(a:done_position['line'] + 1, l:before . l:after) call cursor([a:done_position['line'] + 1, strlen(l:before) + 1]) endfunction diff --git a/test/lsp/omni.vimspec b/test/lsp/omni.vimspec index ec9f0844..b74e3c79 100644 --- a/test/lsp/omni.vimspec +++ b/test/lsp/omni.vimspec @@ -84,6 +84,7 @@ Describe lsp#omni \ 'completion_item': item, \ 'complete_position': { 'line': 1, 'character': 1 }, \ 'start_character': 0, + \ 'complete_word': 'yyy', \ }) End @@ -187,6 +188,7 @@ Describe lsp#omni \ 'completion_item': item, \ 'complete_position': { 'line': 1, 'character': 1 }, \ 'start_character': 0, + \ 'complete_word': 'System.out.println(${0});', \ }) End