私はこの崇高なテキストの例のようにコンテキストに応じて単一のvimバッファ内に2つの異なる背景色を適用するための可能な解決策を探しています。
その使用例の1つは、マークアップファイル内のコードスニペットに異なる色を付けて、目立つようにすることです。
しかし、私はそのようなセットアップの例を見たことはありません。
これはvimで可能ですか?
私はこの崇高なテキストの例のようにコンテキストに応じて単一のvimバッファ内に2つの異なる背景色を適用するための可能な解決策を探しています。
その使用例の1つは、マークアップファイル内のコードスニペットに異なる色を付けて、目立つようにすることです。
しかし、私はそのようなセットアップの例を見たことはありません。
これはvimで可能ですか?
回答:
これがどれだけうまくいくのか興味があったので、そのような作品を一緒にハッキングしました。
前の回答のコメントで述べたように、これを行う唯一の方法は、領域をスペースで埋めることです。これはまさに私たちが行うことです。書く前にこれらのスペースを削除するので、他の人に迷惑をかけないでください。
この例は、マークダウンファイルタイプに非常に限定されていることに注意してください!
副作用:
'list'
有効にすると背景は表示されませんまず、これをに追加する必要があります~/.vim/after/syntax/markdown.vim
:
syn clear markdownCodeBlock
syn region markdownCodeBlock start=" \|\t" end="$"
hi def markdownCodeBlock ctermbg=230 guibg=lightyellow
もちろん、お好みに合わせて色を調整できます;-)
次に、これをvimrcに追加します。
fun! MarkdownBlocks()
fun! s:fill(line)
" Remove all trailing whitespace
let l:line = substitute(a:line, " *$", "", "")
" Add trailing whitespace up to 'textwidth' length
return l:line . repeat(' ', (&tw > 0 ? &tw : 80) - strdisplaywidth(l:line))
endfun
" Get all lines in a list
let l:lines = getline(1, line('$'))
" Map s:fill() to the lines that are a code block
call map(l:lines, 'v:val[0] == "\t" || v:val[:3] == " " ? s:fill(v:val) : v:val')
" Reset the buffer to the lines
call setline(1, l:lines)
endfun
" Remove all the trailing spaces
fun! MarkdownBlocksClean()
let l:save_cursor = getpos(".")
silent %s/^\( \|\t\)\(.\{-}\)\( *\)$/\1\2/e
call setpos('.', l:save_cursor)
endfun
au BufWritePre *.markdown call MarkdownBlocksClean()
" Set spaces on loading the file, leaving insert mode, and after writing it
au FileType markdown call MarkdownBlocks()
au InsertLeave *.markdown call MarkdownBlocks()
au BufWritePost *.markdown call MarkdownBlocks()
コードを行ごとに説明するつもりはありませんが、コメントによってその概要が明確になるはずです;-)
構文が強調表示された要素に異なる背景色を使用することは確かに可能です。コマンドで色guibg
とctermbg
色を定義するだけhilight
です。前者はGUI Vimの背景色を設定し、後者は端末Vimの背景色を設定します。
ただし、これには、ファイルに実際に存在する文字の背景色のみを設定できるという重要な制限があります。
この結果、背景色は行のテキストの終わりを超えてウィンドウの端まで拡張できないため、例に示されているコードブロックの色付けはできません。
署名機能を使用して、行全体の背景色を変更することもできます。(参照linehl
中:help sign.txt
)
ただし、次のことに注意してください。
これを行うには、色を付ける必要がある各行に記号を配置し、ファイルの内容が変更されたときにこれらを更新し続けるコードを記述する必要があります。
デフォルトでは、サインを配置すると、サイン列がウィンドウの左側に表示されます。SignColumn
ハイライトグループでサイン列の色を変更することができ、Vimの最近のバージョンでは完全に削除できます。(を参照してください:help 'signcolumn'
。)
たとえば、Carpetsmokerのソリューションを(より堅牢な)署名メカニズムを使用するように適合させるには、次のようにします。
" Define a highlight group and a sign that uses it
highlight default markdownCodeBlock ctermbg=230 guibg=lightyellow
sign define codeblock linehl=markdownCodeBlock
" Use signs to highlight code blocks
function! MarkdownBlocks()
function! s:applySign(idx, val)
if a:val[0] == "\t" || a:val[:3] == " "
let l = a:idx + 1
execute "sign place " . l . " line=" . l . " name=codeblock file=" . expand("%:p")
endif
endfunction
" Remove old signs
execute "sign unplace * file=" . expand("%:p")
" Get all lines in a list
let l:lines = getline(1, line('$'))
" Add new signs
call map(l:lines, function('s:applySign'))
endfunction
" Set signs on loading the file, leaving insert mode, and after writing it
au FileType markdown call MarkdownBlocks()
au InsertLeave *.markdown call MarkdownBlocks()
au BufWritePost *.markdown call MarkdownBlocks()
これにより、コードが多少簡素化され、Carpetsmokerのバージョンよりも警告が少なくなります。
@ChristianBrabandtのDynamicSignsプラグインは、この目的のために署名機能をより簡単に使用できるようにします。
guibg
gvimでのみ動作します、そうですか?
ctermbg
、前述のようにを使用する必要があります。