Close #4401 - Use subtle defaults for virtual-text

Default virtual-text to the Comment highlight group and prefix
virtual-text messages with comment text for each language by default.

Messages can now be formatted with `%type%` to print the error type.

The Vim 9.0 version has been updated in the Docker image to add test
coverage for virtual-text.
This commit is contained in:
w0rp
2022-12-27 23:11:53 +00:00
parent 98b2ef438e
commit a18472cc58
7 changed files with 343 additions and 100 deletions

View File

@@ -254,6 +254,7 @@ function! ale#GetLocItemMessage(item, format_string) abort
" \=l:variable is used to avoid escaping issues.
let l:msg = substitute(l:msg, '\v\%([^\%]*)code([^\%]*)\%', l:code_repl, 'g')
let l:msg = substitute(l:msg, '\V%severity%', '\=l:severity', 'g')
let l:msg = substitute(l:msg, '\V%type%', '\=l:type', 'g')
let l:msg = substitute(l:msg, '\V%linter%', '\=l:linter_name', 'g')
" Replace %s with the text.
let l:msg = substitute(l:msg, '\V%s', '\=a:item.text', 'g')

View File

@@ -4,7 +4,7 @@ scriptencoding utf-8
" Description: Shows lint message for the current line as virtualtext, if any
if !hlexists('ALEVirtualTextError')
highlight link ALEVirtualTextError SpellBad
highlight link ALEVirtualTextError Comment
endif
if !hlexists('ALEVirtualTextStyleError')
@@ -12,7 +12,7 @@ if !hlexists('ALEVirtualTextStyleError')
endif
if !hlexists('ALEVirtualTextWarning')
highlight link ALEVirtualTextWarning SpellCap
highlight link ALEVirtualTextWarning Comment
endif
if !hlexists('ALEVirtualTextStyleWarning')
@@ -23,11 +23,15 @@ if !hlexists('ALEVirtualTextInfo')
highlight link ALEVirtualTextInfo ALEVirtualTextWarning
endif
let g:ale_virtualtext_prefix =
\ get(g:, 'ale_virtualtext_prefix', '%comment% %type%: ')
" Controls the milliseconds delay before showing a message.
let g:ale_virtualtext_delay = get(g:, 'ale_virtualtext_delay', 10)
let s:cursor_timer = get(s:, 'cursor_timer', -1)
let s:last_pos = get(s:, 'last_pos', [0, 0, 0])
let s:hl_list = get(s:, 'hl_list', [])
let s:last_message = ''
if !has_key(s:, 'has_virt_text')
let s:has_virt_text = 0
@@ -47,72 +51,6 @@ if !has_key(s:, 'has_virt_text')
endif
endif
function! ale#virtualtext#Clear(buf) abort
if !s:has_virt_text
return
endif
if has('nvim')
call nvim_buf_clear_namespace(a:buf, s:ns_id, 0, -1)
else
if s:emulate_virt && s:last_virt != -1
call prop_remove({'type': 'ale'})
call popup_close(s:last_virt)
let s:last_virt = -1
elseif !empty(s:hl_list)
call prop_remove({
\ 'types': s:hl_list,
\ 'all': 1,
\ 'bufnr': a:buf})
endif
endif
endfunction
function! ale#virtualtext#ShowMessage(message, hl_group, buf, line) abort
if !s:has_virt_text || !bufexists(str2nr(a:buf))
return
endif
let l:prefix = get(g:, 'ale_virtualtext_prefix', '> ')
let l:msg = l:prefix.trim(substitute(a:message, '\n', ' ', 'g'))
if has('nvim')
call nvim_buf_set_virtual_text(a:buf, s:ns_id, a:line-1, [[l:msg, a:hl_group]], {})
elseif s:emulate_virt
let l:left_pad = col('$')
call prop_add(a:line, l:left_pad, {
\ 'type': 'ale',
\})
let s:last_virt = popup_create(l:msg, {
\ 'line': -1,
\ 'padding': [0, 0, 0, 1],
\ 'mask': [[1, 1, 1, 1]],
\ 'textprop': 'ale',
\ 'highlight': a:hl_group,
\ 'fixed': 1,
\ 'wrap': 0,
\ 'zindex': 2
\})
else
let l:type = prop_type_get(a:hl_group)
if l:type == {}
call prop_type_add(a:hl_group, {'highlight': a:hl_group})
endif
" Add highlight groups to the list so we can clear them later.
if index(s:hl_list, a:hl_group) == -1
call add(s:hl_list, a:hl_group)
endif
call prop_add(a:line, 0, {
\ 'type': a:hl_group,
\ 'text': ' ' . l:msg,
\ 'bufnr': a:buf
\})
endif
endfunction
function! s:StopCursorTimer() abort
if s:cursor_timer != -1
call timer_stop(s:cursor_timer)
@@ -120,17 +58,58 @@ function! s:StopCursorTimer() abort
endif
endfunction
function! ale#virtualtext#GetHlGroup(type, sub_type) abort
if a:type is# 'E'
if a:sub_type is# 'style'
function! ale#virtualtext#ResetDataForTests() abort
let s:last_pos = [0, 0, 0]
let s:last_message = ''
endfunction
function! ale#virtualtext#GetLastMessageForTests() abort
return s:last_message
endfunction
function! ale#virtualtext#GetComment(buffer) abort
let l:filetype = getbufvar(a:buffer, '&filetype')
let l:split = split(getbufvar(a:buffer, '&commentstring'), '%s')
return !empty(l:split) ? trim(l:split[0]) : '#'
endfunction
function! ale#virtualtext#Clear(buffer) abort
if !s:has_virt_text
return
endif
if has('nvim')
call nvim_buf_clear_namespace(a:buffer, s:ns_id, 0, -1)
else
if s:emulate_virt && s:last_virt != -1
call prop_remove({'type': 'ale'})
call popup_close(s:last_virt)
let s:last_virt = -1
elseif !empty(s:hl_list)
call prop_remove({
\ 'types': s:hl_list,
\ 'all': 1,
\ 'bufnr': a:buffer,
\})
endif
endif
endfunction
function! ale#virtualtext#GetGroup(item) abort
let l:type = get(a:item, 'type', 'E')
let l:sub_type = get(a:item, 'sub_type', '')
if l:type is# 'E'
if l:sub_type is# 'style'
return 'ALEVirtualTextStyleError'
endif
return 'ALEVirtualTextError'
endif
if a:type is# 'W'
if a:sub_type is# 'style'
if l:type is# 'W'
if l:sub_type is# 'style'
return 'ALEVirtualTextStyleWarning'
endif
@@ -140,8 +119,67 @@ function! ale#virtualtext#GetHlGroup(type, sub_type) abort
return 'ALEVirtualTextInfo'
endfunction
function! ale#virtualtext#ShowMessage(buffer, item) abort
if !s:has_virt_text || !bufexists(str2nr(a:buffer))
return
endif
let l:line = a:item.lnum
let l:hl_group = ale#virtualtext#GetGroup(a:item)
" Get a language-appropriate comment character, or default to '#'.
let l:comment = ale#virtualtext#GetComment(a:buffer)
let l:prefix = ale#Var(a:buffer, 'virtualtext_prefix')
let l:prefix = ale#GetLocItemMessage(a:item, l:prefix)
let l:prefix = substitute(l:prefix, '\V%comment%', '\=l:comment', 'g')
let l:msg = l:prefix . substitute(a:item.text, '\n', ' ', 'g')
" Store the last message we're going to set so we can read it in tests.
let s:last_message = l:msg
if has('nvim')
call nvim_buf_set_virtual_text(
\ a:buffer,
\ s:ns_id, l:line - 1,
\ [[l:msg, l:hl_group]],
\ {}
\)
elseif s:emulate_virt
let l:left_pad = col('$')
call prop_add(l:line, l:left_pad, {'type': 'ale'})
let s:last_virt = popup_create(l:msg, {
\ 'line': -1,
\ 'padding': [0, 0, 0, 1],
\ 'mask': [[1, 1, 1, 1]],
\ 'textprop': 'ale',
\ 'highlight': l:hl_group,
\ 'fixed': 1,
\ 'wrap': 0,
\ 'zindex': 2
\})
else
let l:type = prop_type_get(l:hl_group)
if l:type == {}
call prop_type_add(l:hl_group, {'highlight': l:hl_group})
endif
" Add highlight groups to the list so we can clear them later.
if index(s:hl_list, l:hl_group) == -1
call add(s:hl_list, l:hl_group)
endif
call prop_add(l:line, 0, {
\ 'type': l:hl_group,
\ 'text': ' ' . l:msg,
\ 'bufnr': a:buffer,
\})
endif
endfunction
function! ale#virtualtext#ShowCursorWarning(...) abort
if g:ale_virtualtext_cursor isnot# 'current' && g:ale_virtualtext_cursor != 1
if g:ale_virtualtext_cursor isnot# 'current'
\&& g:ale_virtualtext_cursor != 1
return
endif
@@ -155,23 +193,19 @@ function! ale#virtualtext#ShowCursorWarning(...) abort
return
endif
let [l:info, l:loc] = ale#util#FindItemAtCursor(l:buffer)
let [l:info, l:item] = ale#util#FindItemAtCursor(l:buffer)
call ale#virtualtext#Clear(l:buffer)
if !empty(l:loc)
let l:msg = l:loc.text
let l:type = get(l:loc, 'type', 'E')
let l:style = get(l:loc, 'sub_type', '')
let l:hl_group = ale#virtualtext#GetHlGroup(l:type, l:style)
call ale#virtualtext#ShowMessage(l:msg, l:hl_group, l:buffer, line('.'))
if !empty(l:item)
call ale#virtualtext#ShowMessage(l:buffer, l:item)
endif
endfunction
function! ale#virtualtext#ShowCursorWarningWithDelay() abort
let l:buffer = bufnr('')
if g:ale_virtualtext_cursor isnot# 'current' && g:ale_virtualtext_cursor != 1
if g:ale_virtualtext_cursor isnot# 'current'
\&& g:ale_virtualtext_cursor != 1
return
endif
@@ -198,19 +232,16 @@ function! ale#virtualtext#ShowCursorWarningWithDelay() abort
endif
endfunction
function! ale#virtualtext#SetTexts(buf, loclist) abort
function! ale#virtualtext#SetTexts(buffer, loclist) abort
if !has('nvim') && s:emulate_virt
return
endif
call ale#virtualtext#Clear(a:buf)
call ale#virtualtext#Clear(a:buffer)
for l in a:loclist
if l['bufnr'] != a:buf
continue
for l:item in a:loclist
if l:item.bufnr == a:buffer
call ale#virtualtext#ShowMessage(a:buffer, l:item)
endif
let l:hl = ale#virtualtext#GetHlGroup(l['type'], get(l, 'sub_type', ''))
call ale#virtualtext#ShowMessage(l['text'], l:hl, a:buf, l['lnum'])
endfor
endfunction