なんだか妙に時間が空いてしまったのだけど、続き。
ys 系で新しく包囲文字列を挿入するのを考える。このとき、モーションによって生成される内部的な選択範囲か、あるいは visual モードでの明示的な選択範囲が対象になるわけなのだが選択範囲が文字志向か行志向かで挿入される位置などが若干違う。
文字志向の場合
- 基本の動作は、選択範囲の両端点に左右の包囲文字列を挿入する
- レジスタの内容は、選択範囲の内容であり、やはり文字志向である。無名レジスタは変更されない。従って再利用できるとしたら [cci]”1[/cci] または [cci]”-[/cci] レジスタのどちらかになる
- ys の前にカウンタが指定されている場合、無視される。モーションおよびテキストオブジェクトに対するカウンタはそれらに対してのみ参照され、surrounding に対しては使用されない
- 挿入後、カーソルは選択範囲の左の端点に挿入した包囲文字列の先頭位置に置かれる
- undo は両端点に対する挿入が一つのクラスタにまとめられた単位
行志向の場合
- 基本の動作は、選択範囲の左端点には左の包囲文字列 + 改行、右端点には改行 + 右の包囲文字列を挿入する。選択範囲の内容は適切にインデントする
- レジスタの内容は、選択範囲の内容であるが、何故か文字志向であるのを含めて ys と同様
- カウンタの扱いは、ys と同様
- 挿入後のカーソル位置は、ys と同様
- undo の単位も ys と同様に挿入される一式が単一クラスタになる
というわけで双方で異なるのは選択範囲に実際に挿入される包囲文字列なのだが、「結果的に双方で同じ」なのがレジスタの内容だ。このへんの重箱の隅はそんなに合わせる必要はないかもしれない。
* * *
ところでさらにいくつか気がかりな点がある。vim のテキストオブジェクトには [cci]t[/cci] がある。これは SGML のタグを表す。しかし wasavi ではこれを実装していないのである。
wasavi の Range Symbols というのは、実は vim の search.c の目コピーなので単にそこから移植すればいいのだけれど、前にも書いたと思うが行中のタグを見つけるというのは本来シンタックス・パーザーの仕事なのである。Range Symbol クラスがそれのサブセットを持つのは無駄だ。なので、実装するにしても色分けその他諸々を先に片付けた上でその成果物を利用して…みたいに考えていた。
がしかし Surround.vim を実装するとなるとやはり [cci]t[/cci] がないと魅力半減な感じはすごくする。うーんどうしたものかな。
もうひとつ。複数行に対して包囲した場合、その内容がインデントされるのだが。このインデント処理とは具体的に何かといえば、vim で言うところの [cci]'[=’][/cci] なのである。wasavi は [cci]=[/cci] コマンドを実装していない。これも本来はファイルタイプに応じたインデント処理を実装するのが先のはずなのだけど。