反省はしても後悔はしない

Vim とか備忘録とか。それと関数型言語勉強中

Vim で Ruby の def end とかを自動入力する vim-endwise を vim-smartinput で実装してみた

この記事は Vim Advent Calendar 342 日目の記事です。 昨日は id:leafcage さんの README.mdをVimのヘルプファイルから生成する - cafegale でした。とても素晴らしいプラグインですね。本プラグインでも早速活用させていただきました。

vim-endwise について

例えば Ruby では様々な構文の終わりを end というキーワードで表します。という訳で Ruby ではコードが end だらけになるわけですがこれをいちいち手で打つのは面倒です。これの自動入力を行ってくれるのが tpope/vim-endwise です。 例えば、

f:id:cohama:20131108004248p:plain

このときに <CR> を打つと、

f:id:cohama:20131108004315p:plain

このように end が自動で挿入されます。便利! Ruby の他には Lua, Vim script, sh, VB, Elixir に対応しています。

vim-smartinput と vim-endwise の問題点 について

ところで、私の大好きなプラグインのひとつに kana/vim-smartinput があります。これは (){} の自動入力を行ってくれるものです。 例えば、

f:id:cohama:20131108004351p:plain

このときに { を打つと、

f:id:cohama:20131108004402p:plain

さらに <CR> を打つと、

f:id:cohama:20131108004412p:plain

このように } が自動で挿入されます。C や JavaScript などの中括弧系の言語に便利ですね!

で、この2つのプラグインやってることは似ています。Ruby などの end を使う系は vim-endwise 、JavaScript などの {} を使う系は vim-smartinput という使い分けをしたいですね。

が、残念なことにこの2つのプラグインは競合します。両者ともインサートモード時の <CR> をマッピングしてしまうためです。 私は以前はこのようにして解決していました。

vim-smartinput と vim-endwise が競合した時の対処法 - 反省はしても後悔はしない

という訳で vim-smartinput を使って vim-endwise を実装してみた

vim-smartinput は Vim 界の神こと kana さん作のプラグインであり、非常に高い拡張性を持っています。つまり、vim-smartinput さえあれば vim-endwise の機能は実装できるのです!!

という訳で実装しました。

cohama/vim-smartinput-endwise · GitHubcohama/vim-smartinput-endwise

インストール方法は NeoBundle の場合は

NeoBundle "kana/vim-smartinput"
NeoBundle "cohama/vim-smartinput-endwise"

call smartinput_endwise#define_default_rules()

と書けば OK です。

これで vim-smartinput ひとつで全て実現できるので競合の問題は解決です。さらに、neocomplcache などを使っていると、補完ウィンドウと競合することがあるので、neocomplcache / neocomplete に対しても特別な競合対策を施してあります。 他のプラグインとの競合が極力避けらルのが本プラグインのメリットです。

一応機能としては vim-endwise になるべく近くなるように実装しています。コメントや文字列では展開されないといったことは実現できています。ただ、やはりある機能だけに特化したプラグインと汎用的なプラグインの差というのはどうしてもあります。具体的には searchpair を使った「すでに end などのが入力されていたらそれ以上 end を入力しない」ということを vim-smartinput で実装するのは難しくてやっていません。

あと、現在対応している言語は Ruby, Vim script, sh (zsh) の 3 つだけです。他のやつはほとんど書いたことないのでやる気が出ませんでした。もし必要なら issue とかに上げてもらえると対応するかもしれません。

おわりに

  • vim-smartinput は素晴らしいプラグインなのでみなさん使いましょう。
  • プルリク待っています
  • そして私は def end の展開には neosnippet を使っているのであった...

明日は @Linda_pp さんです。