LoginSignup
13
16

More than 5 years have passed since last update.

Vimでの日本語入力・編集用に別コマンドを割り当てる

Posted at

Vim Advent Calendar 2013の105日目(2014-03-15)の記事です。

日本語入力IMをオンにしてInsert modeを開始するコマンドをmapする
Vimプラグインimactivatemap.vimを作りました
(i,a,c,o等に対して、日本語入力オンで開始するgi,ga,gc,go等をmap)。
Insert modeに入る際には、日本語を編集したいことは意識しているので、
その意図を直接表現するコマンドを用意すると気持ち良く操作ができるかと思って作ってみました。

c,s,rコマンドで、書き換え前の文字列に応じてIMオン/オフを切り替えるVimプラグインを作ったのですが、
日本語入力オン/オフ制御が意図から外れる場合がたまにあってストレスになるので、
逆方向のアプローチとして、日本語で編集することを指定するコマンドを割り当てる方法のプラグインです。
vi的には、日本語入力IMオンにしてInsert modeを開始するコマンドを用意する方が自然な気がしたので。

さらに、Insert modeのままでのIMオン/オフ切り替えは使わずに、
オンに切り替えたい場合は一度Insert modeを抜ける形にするのがvi的かもしれません。
つまり、以下の2種類のコマンドとみなす形。

  • iで始まり、ASCII文字列を入力して、Escで終わるコマンド。
  • giで始まり、日本語文字列を入力して、Escで終わるコマンド。

この場合は、以下のようにInsert modeを抜けるとIMオフになるように設定しておいてください。

 inoremap <silent> <unique> <Esc> <Esc>:set imsearch=0 iminsert=0<CR>

特徴

  • 新たなモードの追加無しに、vi操作中に日本語編集を融合 (日本語入力固定モード のように、IMEオン固定モードとIMEオフ固定モードを追加して切り替えるのではなく)
    • までの文字列をIMオフで編集するcgtがや、 hまでの文字列をIMオンで編集するgcth等の組み合わせも可。
  • 現在の日本語入力モードがオンかオフかを意識しなくて良い。 gaでInsert modeを始めれば常に日本語入力オンで入力できますし、 aで始めれば常に日本語入力オフで入力できます。
  • Insert mode中に日本語入力オンオフ切り替え操作をしなくて良い。 かわりにEscで抜けてInsert modeに入り直す操作が多くなりますが。

欠点

iのかわりにgiを入力する必要があるので、操作が少し長くなります。

日本語入力メインで行う場合は、iのかわりにgiを打つのは面倒なので、
Insert modeを抜けてもオフにしない方がいいかもしれません。
(その場合は、日本語入力オフでInsert modeを開始するコマンドを、
qi等に割り当てておくのがいいかも。)

このあたりは、viを使い始めた時にiを打つのを面倒に感じたのと同様に、
慣れの問題かもしれないので、しばらく使ってみる予定です。

少し使ってみての感想

  • Insert modeに入ってからIMを切り替えるよりも、ga等のコマンドを使う方が楽な印象。 たとえ、Escで抜けてgaを押してIMをオンにし直さないといけない場合でも。 IM切り替えはコントロールキーを使うからかも。
  • g/で直接日本語入力を開始できるのは便利。 CTRL-^を押して切り替えるのは面倒だったので。
  • 日本語編集をするつもりなのにgcでなくcを押してしまう場合がよくある。 同様にaiでも。この場合、一度Escで抜けてgcを押し直す形。 慣れると意識せずにできるようになるか?
  • 一番良く使うのはga。逆に、日本語入力をするつもりが無いのに押してしまって、 一度Escで抜けてaを押し直すことも。 その他便利なのはgsgcは少し考えないとまだ使えない。
  • Vim以外のアプリではIMオン/オフ操作が必要なので、操作の統一性が無くなるため、 意識のスイッチが必要。 (Vimを使う時点である程度スイッチしているので慣れればほぼ無意識にできるはず?)

mapするキー

デフォルトでは、日本語入力IMオンにして編集を開始する以下のキーをmapします。

  • gi, gI, ga, gA, go, gO, gs, gS, gc, gC, gr, gR
  • gf, gF, gt, gT
  • g/, g?

デフォルトでは、打ちやすさを考慮してgに割り当てていますが、
gi, gI, ga, go, gs, gr, gR, gf, gt, g?を上書きしてしまいます。
他のキーに割り当てるには、g:imactivatemap_prefixkeyを設定してください。

  let g:imactivatemap_prefixkey = 'q'

候補となるprefixキー:

  • q: 少し打ちにくい。
  • m: ma等はよく使うので、指が意識せずに動いてしまっていまいち。
  • s: clで代替可能なので。ただ個人的にsはよく使うのでつぶしたくない。

IMのオン/オフの切り替え制御

IMのオン/オフの切り替え制御は、デフォルトでは
&iminsert&imsearch(/,?向け)の値を2や0に設定することで行います。
(Windowsのgvimの場合など。)

その他のIM切り替え方法に関しては、以下を参考にしてください。

IM切り替え方法のカスタマイズをしたい場合は、
IM切り替えを行う関数を定義して、
その関数名をimactivatemap_imifuncimactivatemap_imsfuncに設定してください
(以下の設定例も参考)。

関数の引数は'imactivatefunc'と同じです。

これらのカスタマイズした関数をIMオフ目的で呼ぶ<Plug>として、
<Plug>(imactivatemap-reset)をnnoremapしてあります。
Insert modeをEscで抜けるとIMオフになるように設定するには、

 inoremap <silent> <unique> <Esc> <Esc>:set imsearch=0 iminsert=0<CR>

のかわりに

 imap <silent> <unique> <Esc> <Esc><Plug>(imactivatemap-reset)

と設定してください。

設定例: tcvime(1.5.0)の場合

tcvimeはkeymapを使うので、
tcvime#Activate()では、&iminsertの値を1や0に設定しています。

.vimrc
" g/, g?, /, ?の検索でIMのオン/オフを切り替えるため、imsearchをセットする関数
function! ImActivateMapImsFunc(active)
  if !a:active
    set imsearch=0
    return
  endif
  if &keymap != ''
    set imsearch=1
    return
  endif
  " keymap未設定時はロードが必要
  call tcvime#Activate(1)
  set imsearch=1
  " tcvime#Activate(1)で&imi=1になるが、g/直後のa等ではオフにしておきたいので
  call tcvime#Activate(0)
endfunction
let imactivatemap_imsfunc = 'ImActivateMapImsFunc'
let imactivatemap_imifunc = 'tcvime#Activate'
imap <silent> <unique> <Esc> <Esc><Plug>(imactivatemap-reset)

関連

13
16
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
13
16