Vimでmarkdownの箇条書き
- 箇条書き
- 箇条書き
1. 番号リスト
1. 番号リスト
> 引用
> 引用
> > 入れ子になった引用
> > 入れ子になった引用
↓
- 箇条書き
- 箇条書き
- 番号リスト
- 番号リスト
引用
引用入れ子になった引用
入れ子になった引用
こういう箇条書きをvimで書きやすくする設定を紹介します。
改行したときに、自動的に箇条書きが継続されるようになります。
改行したときに自動的に箇条書きを継続する設定
オプションのcomments
とformatoptions
を調整します。
markdown限定の処理なので、(runtimepath)/after/ftplugin/markdown.vim
に定義してください。
setlocal comments=b:*,b:-,b:+,b:1.,nb:>
setlocal formatoptions-=c formatoptions+=jro
comments
の設定(:h format-comments
)
-
:
の後ろ: コメント文字列 -
:
の前: フラグ文字列-
b
: コメント文字列の後ろにホワイトスペースを必要とする指定(-1
などを除外するため) -
n
: 入れ子を許可する指定
-
formatoptions
の設定(:h fo-table
)
-
j
: ノーマルモードでJ
で行を連結するとき、連結された行の先頭のコメント文字列を削除する -
r
: 挿入モードで改行するとき、行頭に現在のコメント文字列を自動挿入する -
o
: ノーマルモードでo
O
で挿入モードに入るとき、行頭に現在のコメント文字列を自動挿入する -
c
:textwidth
で自動改行する
<CR>
のマッピングを操作しないため、補完プラグインなどのマッピングに影響されず使用可能です。
チェックボックス記法への対応
リストに続いて[ ]
または[x]
を入力するとチェックボックスになる記法があります。リストマーカー直後以外の場所や、[]
[a]
などではチェックボックスになりません。
[ ] not check box
- list [ ] not checkbox
- [] not check box
- [a] not check box
- [ ] blank box
- [x] checked
↓
[ ] not check box
- list [ ] not checkbox
- [] not check box
- [a] not check box
- blank box
- checked
この場合もcomments
オプションで設定できますが、チェックボックス記法を通常のリストより先に指定します。また、スペースをバックスラッシュでエスケープする必要があります。
ここではリストマーカー(*
+
-
)を全種類定義していますが、-
しか使わないよ、といった場合は適宜減らしてください。
setlocal comments=nb:>
\ comments+=b:*\ [\ ],b:*\ [x],b:*
\ comments+=b:+\ [\ ],b:+\ [x],b:+
\ comments+=b:-\ [\ ],b:-\ [x],b:-
\ comments+=b:1.\ [\ ],b:1.\ [x],b:1.
\ formatoptions-=c formatoptions+=jro
チェックボックスを切り替えるマッピング
こちらの:MarkdownCheckbox
コマンドを定義すれば、上記のチェックボックスの切り替えが簡単になります。
function! s:markdown_checkbox(from, to) abort
let from = a:from
let to = a:to
let another = line('v')
if from == to && from != another
if another < from
let from = another
else
let to = another
endif
endif
let curpos = getcursorcharpos()
let lnum = from
while lnum <= to
let line = getline(lnum)
let list_pattern = '\v^\s*([*+-]|\d+\.)\s+'
if line !~ list_pattern
" not list -> add list marker and blank box
let line = substitute(line, '\v\S|$', '- [ ] \0', '')
if lnum == curpos[1]
let curpos[2] += 6
endif
elseif line =~ list_pattern .. '\[ \]\s+'
" blank box -> check
let line = substitute(line, '\[ \]', '[x]', '')
elseif line =~ list_pattern .. '\[x\]\s+'
" checked box -> uncheck
let line = substitute(line, '\[x\]', '[ ]', '')
else
" list but no box -> add box after list marker
let line = substitute(line, '\v\S+', '\0 [ ]', '')
if lnum == curpos[1]
let curpos[2] += 4
endif
endif
call setline(lnum, line)
let lnum += 1
endwhile
call setcursorcharpos(curpos[1], curpos[2])
endfunction
command! -buffer -range MarkdownCheckbox call s:markdown_checkbox(<line1>, <line2>)
- リストでない場合 → リストとボックスを追加
- リストだがチェックボックスがない場合 → ボックスを追加
- チェックされていないボックスの場合 → チェック
- チェックされたボックスの場合 → チェック解除
前述のcomments
指定と合わせて、ftpluginでbuffer限定でマッピングを追加するのがおすすめです。以下では<C-CR>
に設定しています。
" MarkdownCheckboxの定義は省略
" setlocal commentsの定義は省略
nnoremap <buffer> <C-CR> <Cmd>MarkdownCheckbox<CR>
inoremap <buffer> <C-CR> <Cmd>MarkdownCheckbox<CR>
xnoremap <buffer> <C-CR> <Cmd>MarkdownCheckbox<CR>
normal/insert/visualの各モードで、<C-CR>
でチェックボックスを切り替えられるようになります。
なお、visualモードに対応したマッピングについては以下の記事をご覧ください。
Discussion