テキストエディタ(WinVi)
本ソフトウェアは、1996年の秋に私が初めて手掛けたWindowsのプログラムです。それまではずっとUNIX上で仕事をしていたのですが、その頃からWindowsでの作業が増えてきました。しかしUNIXあがりの私はviオペレーションが脳髄反射レベルで染み付いていてとてもメモ帳に移行する気になれません。ところがその当時はWindowsでまともに動くviがありませんでした(あったのかもしれませんが、調査能力の低い私は知り得ませんでした)。まあそんな訳で、ゼロから自分で作り込むことにしました。初期のコーディング作業はDOSプロンプトで動くvi(確かsteveというソフトだったと記憶しています)を使いました。漢字は使えないし当時のDOS窓は640×400固定という劣悪な環境での開発スタートでした。ある程度開発が進み、自分が開発しているviでそれ自体のコーディングをし始めた瞬間の感動は今でも忘れられません。この時に確立した開発スタイルは、WinViでコーディングしDOSプロンプトでVCコンパイルするというものです。昨今の統合開発環境と比べるとひどく原始的ですが、これが私には最適な開発スタイルであり、未だにこのスタイルで開発し続けています。閑話休題。という訳でこのエディタは自分自身のために開発しました。プログラムだけでなくメールもこれで書き、ホームページの作成やMusingもこれ一本でやってきました。17年間使い込み磨き上げ、今では私にとって一番使いやすいエディタです。今般、長年の使用で溜め込んだ課題を一気に解決し全面リニューアルしました。そしてこれを機会に公開してみることにしました。さりとて、自分が使う機能しかサポートしていませんし、今ではWindows上で動作するも
っと高機能で本格的なviが存在しているので公開意義の希薄感は否めません。然るにメニューさえ持たずDLLも存在せず、そして256Kbyteにも満たないという極度なコンパクトさ故、気に入ってくれる方もいるかもしれないと秘かに期待しています。そしてまさにこのフィールこそが本来の伝統的なUNIX-viの真髄なのではないか、とさえ思っているのです。とは言うものの「自己満足」と「思い込み」と「天邪鬼」を遍く詰め込んだ、実に「身勝手」かつ「独り善がり」なソフトウェアとなっておりますので、そこの所よろしくお願いします。(2013年 秋)
ユーザインターフェースを思索するという点で、テキストエディタの開発ほどエキサイティングな題材はないのではないかと思います。その機能がペンの様に自然で手に馴染むものであればある程、そしてその存在そのものが空気の様に希薄であればある程、文章あるいはコードというコンテンツの創作行為に、利用者が没頭できるからです。そんな特性を持ったソフトウェアを開発するに当たって、私なりに丹念に設計をしたポイントを以下にご紹介したいと思います。
カーソル移動やスクロールの機能セット
エディタ利用において最も使用頻度の高い操作はカーソルやページの移動であろう。それが如何に迅速に実施できるかでエディタの優劣が決まると言っても過言ではない。オリジナルのviもそれを裏付けるかのように多彩なカーソル移動キーを提供している。しかし機能キーが多過ぎると各局面に応じて使い分けることに翻弄されてしまうのも事実である。理想は、シンプルで数が少ないにもかかわらず殆どの局面に対応可能な機能セットの実現である。WinViではオリジナルviでの基本カーソル移動キー[h][j][k][l]に、[CTRL]を組合わせてそれを目指した。[^J][^K]にてカーソル位置を変えないページスクロール、[^H][^L]である程度の間隔を置いたカーソル移動をする。ページ切替えはオリジナルviと同じキーアサイン[^F][^B]とした。総計10種類、分類としては4つしかないため習熟は容易であり、しかもこのセットだけで充分素早くカーソル移動を実施できる。組合せキーを[CTRL]に限定し[SHIFT]を排除したことで、ミスオペレーションも軽減する。特に[^H][^L]は、縦と横の方向で素早く位置決めする概念で、慣れると簡便に目的近傍へカーソルを持っていける。
新発想のマークコマンド
従来のviはmに続くアルファベット指定で複数の行マークを登録できた。対してWinViは1種類のみである。この仕様は『活用するのはほとんどマーク"a"のみ。使ってもせいぜい"b"まで』という私自身の体験に基づいている。仕様としては従来のviとほぼ同等であり、シングルコーテーションでそこにジャンプしたりコマンドの行番号指定で利用できる。異なる点はシングルコーテーションに添えるアルファベットIDが不要であることぐらいだ。マーキングを行うコマンドは[ma]であるが、2ストローク目のaは識別子ではなく限定子であり、a以外のアルファベットは受け付けない。マーク種を1つのみにしたことで、範囲で作用させる各種機能指定が簡便となった。例えば、ある行で[ma]を発行し他の行にカーソルを移動して[md]と入力すれば直ちにその間の行が削除される。削除[md]の他にも範囲指定系の機能群を多数サポートした。クリップボード登録[mt]、ヤンクバッファ登録[my]、ヤンクバッファ追加[mk]、行頭タブ追加[m>]、行頭タブ削除[m<]、文字削除[mx]、文字置換[ms]である。これらの機構により従来のviの様に行数や行番号、文字数などを意識する必要がなくなった。なお、[my][mk][mt]のバッファ処理系機能は、[ma]と同一行で発行された場合は文字単位の処理を行い、異なる行の場合は行単位の処理を行う。また、"m"マークが未定義の場合、起点として行頭位置が採用され、そこが新たな"m"マークになる。この仕様により、行頭からカーソル位置までの処理機能として利用することも可能である。"m"マークを積極的に未定義にしたい場合は、[ESC]の押下でそれを可能とした。なお基本的に行内範囲を扱う[mx][ms]で、現カー
ソル行とマーク行が異なる場合は、現カーソル行の行頭を起点として処理する。
ヤンクバッファの累積追加
従来のviはヤンクバッファへの格納を行うと、直前まで記憶していたバッファ内容が入れ替わる。そのため場所が離れている複数行を他の位置にまとめて複写したい場合には、コピー元とコピー先の行を何度も往復する必要があった。レジスタという概念でそれをクリアしているviもあるが、少々手数が多くて気軽に利用しにくい。WinViは直前まで記憶していたバッファをクリアせず累積的に追加していく機能[K]を提供している。ある行で[Y]を発行してヤンクバッファに格納後、他の行で[K]を発行するとバッファに追加される。以降[K]を繰返せば、ヤンクバッファに次々と累積され、最後に[p]あるいは[P]の発行で今まで累積した行を一気に挿入できる。オリジナルのviは、行をヤンクに登録するキーが[Y]と[yy]で重複定義されており、しかも文字単位のヤンク登録が存在しない。そこでWinViでは[yy]を文字単位ヤンク登録として新設した。結果として、大文字[Y]が行単位のヤンク登録、小文字yで始まる[yy]と[yw]が文字単位のヤンク登録となり、統一感のある美しい仕様になった。
コマンドでの行番号指定
Winviは行番号の加算減算などの演算機構を持っていない。私が過去それを必要と感じる局面がなかった事が理由であるが、しかし例えばある行から100行を削除したいといった場合は時折存在する。従来のviであれば、:.,.+99として指定できるが、Winviではもっと簡便な方法を提供することにした。この例では、:+100 と入力すればよい。現カーソル位置よりも上部の行を指定することはできないが、行数指定の場合は他のコマンドも下行に向かってのカウントなので問題はないと考えている。むしろ、16dd と :+16d の処理内容が一致する点で美しい仕様なのではないだろうか。この他にもマークした行から現在の行まで、あるいは現在の行からマークした行までを指定したい場合もよくある。従来のviであれば、:'a,. あるいは :.,'a となるが、WinViでは、:- のみでそれを実現する。開始行と終了行の前後関係はWinViが内部で整合するので、とにかく[ma]でマークしてカーソル移動し :- とすればよい。
カーソル幅と色設計
カーソル幅が半角や全角の文字占有幅となるのは極めて常識的な話であるが、タブにもこの概念を適用した。特に入力モードにおいてリアルタイムに幅が変化するため、次のタブ位置に移行するタイミングが容易に把握でき、編集ストレスが大幅に軽減する。カーソル色は、タブおよび改行(すなわち空行)において灰色に変化させた。これにより空白部分がスペースによるものか、タブや改行によるものかが、容易に識別できるようになった。よく、タブや改行位置に特殊文字を表示する方式を見かけるが、表示コンテンツと交錯し煩雑になる。本方式はカーソルを確認箇所に位置づける必要があるが、コンテンツの簡潔な視認性と文字の識別性を両立させる仕様だと考えている。入力モードに入るとカーソル色は青碧色に変化し、更にIMEに入ると紅柿色に変化する。青碧色と紅柿色は補色関係にあり変化を感じやすいはずだ。通常モードは無彩色、入力モードは有彩色という思想で設計した。予約語に応じた文字自体の色別け機構はあえてサポートしていない。穿った見解かもしれないが、派手な色分けは必要以上に構造にのみ目を向けさせ、かえってコンテンツに対する熟慮性を損なわせるというのが私見である。
全角モードの判定
半角と全角が混在したテキストを編集していると、半角を打とうとしたのに全角変換モードで始まったり、その逆が起こったりしてストレスが溜まる。特に2ストロークで文字を入力する[r]機能の場合に多い。そこで、ささやかな工夫であるが、[r]機能が発行された時点でカーソル位置の半角/全角を判断し、そのモードでIMEが起動するようにした。どのモードで編集が開始されるかがカーソル位置の文字タイプであらかじめ把握できる。実際に利用してみるとかなり使い勝手が良い。そこでこの自動判定の機構は[r]以外に、[s][ms][C][cw]といった文字を差し替えるタイプの機能に一貫して導入することにした。一方挿入系の[i][a][I][A][o][O]などは判定条件が曖昧なため、直前で使用したIMEモードを維持する仕様とした。なお全角に関してもう1つ有効な機能、アンダーバー[_]を追加した。英字の大文字と小文字を切替えるチルダ[~]と同じ操作感で全角と半角を切替える。
マウスバッファの新設
基本的にはキーボードホームポジションを尊重する設計としたが、部分文字列の始終点を指定するのはやはりマウスオペーレーションの方が手軽であることは否めない。そこでヤンクバッファやクリップボードとは別のマウスバッファという概念を導入した。複数行の扱いはむしろキーボードの方が簡便であるため、マウスバッファはあくまでも行内の文字列に特化することにした。指定方法もviらしく省力化を追求し、対象文字列をマウスでスィープするだけである。文字列を選択してから格納キーを押下するといった操作は不要だ。貼付け操作もマウス右ボタン押下のみとした。入力中の本文へも、最下行のコマンド入力エリアへも貼り付けが可能だ。マウスバッファは複数のWinVi間でデータのやり取りができるため、クリップボード内容を温存したまま、別のデータをやり取りしたい時に便利だ。また、マウスバッファにセットする際に他のバッファへの移送も同時に実施ことも可能だ。[CTRL]キー併用のマウススイープでクリップボードに、[SHIFT]キー併用でヤンクバッファにコピーされる。よって、[CTRL]と[SHIFT]の両方を押下してマウススイープすると、マウスバッファ、ヤンクバッファ、そしてクリップボードの3バッファに一気に同一内容がコピーされることになる。
クリップボードとのやり取り
Windowsを前提としたアプリケーションの場合、やはりクリップボードによるデータのやり取りは避けて通れない。WinViでもそのインターフェースをいくつか準備した。クリップボードにデータを送る操作の基本は[t]で、現カーソル行がクリップボードに送信される。複数行を送信したい場合は所望の行数に続けて[t]を押下すればよい。この[t]には"m"マーク機構も準備されており、[ma][mt]によりその範囲の行がクリップボードに送信される。行内の部分文字列を送信したい場合は、同一行内で[ma][mt]を発行すればよい。また、部分文字列の場合はマウスを利用する方法も準備した。[CTRL]を押下しながらマウススィープすれば、その文字列がクリップボードに送信される。コロンコマンド[:t]による行番号間の複数行送信も可能である。一方、クリップボードから受け取る場合は [:r]あるいは[:R]コマンドとなる。前者は現カーソル直下に、後者は現カーソル直上に、複数行のクリップボード内容が挿入される。なお、[:r]と[:R]はパラメータにファイル名を与えると従来のviと同様、クリップボードではなく指定ファイルを挿入するコマンドとして機能する。入力モードにおいて[^V]を押下すると、そこにクリップボードの文字列を挿入することも可能だ。[^V]はコマンドの文字列にも同様に挿入できる。この様に[^V]は行ではなく文字列の挿入として機能する。よってクリップボードに複数行がセットされている場合でも、その最初の一行のみを展開する仕様とした。一方[^C]はヤンクバッファの内容をクリップボードにコピーする。こちらの方は、ヤンクバッファの内容が文字列であっても複数行であっても、それをそのままコピー
する。1つのWinViでxやddを使い、文字や行を消去した後[^C]を押下すれば、その内容がクリップボードに転送されるため、他のWinViで[:r]あるいは[:R]を使えば、WinVi間の移動処理として活用できる。
曖昧インクリメンタルサーチ
検索キーの確定を待つことなく入力に即応して該当行を絞り込んでいく逐次検索(インクリメンタルサーチ)は、ラフにターゲットを絞り込んでいくタイプの検索に極めて有効である。これをWinViでは、インタラクティブなファイル内grepの如く駆動する機能として提供した。[#]の押下で逐次検索のモードに移行し、行頭に赤のラインが描画される。また、後述する行のダブルクリック操作を容易にするため、マウス位置に行カーソルが出現する。検索キーワードは、ウィンドウ下部のコマンド行に入力する。ここでの検索マッチングは、その主旨を勘案し曖昧性を重視した。英字の大文字小文字はもとより、半角全角、カタカナひらがなの区別もない。
また各種記号も類似性を考慮して検索してくれる。例えば"ア"を検索すると"アあアぁァ"がヒットする。この際、検索キーを分かち書きにするとAND検索となる。OR検索したい場合は1カラム目に"|"を指定する。"|"自体を検索文字として扱いたい場合は、1カラム目を避け2カラム目以降に入力すればよい。絞込み結果が1ページに収まりきらない場合は、表示関係の制御キー[^J][^K][^F][^B]が利用できる。また[↓][↑]キーやマウスホイールによるスクロールも利用できる。本モード中でもマウススィープによるヤンク、クリップ、マウスの各バッファへのコピーも可能である。通常モード復帰は[ENTER]の押下で行う。その際、絞込み結果がクリップボードに出力される。クリップボードへ出力せず復帰させたい場合は[ESC]を押下する。もう一つの有効な復帰方法として、マウスのダブルクリックによる絞込状態と通常状態を往復できる機構を準備した。絞込状態で任意行をダブルクリックすると、その行にカーソルが位置づけられて復帰し、通常状態で任意箇所をダブルクリックすると直近の絞込状態に戻る。これを利用すると、あたかも目次と本文を行き来するイメージで作業することが可能だ。
グローバル処理のオプション
WinViは"sed"をサポートしていないし、"ex"のスーパーセットにもなっていない。その代わり「該当行に一括して行レベルの処理を実施する」というグローバル処理を充実させ実用的なオプションを各種取り揃えることにした。オリジナルのviではこのコマンドに[:g]が割り当てられているが、発行頻度の高さから思わず[:s]で入力を開始してしまうことが多い。考えてみると第2パラメータの有無で[:g]と[:s]は識別可能なのであるから、少々大胆ではあるが[:g]を廃し[:s]でグローバルコマンドを発行することとした。用意したオプションは多彩である。具体的には、行の削除/d 追加/Pp 結合/Jj 入替/Xx 分割/Z ユニーク化/U だ。またこれらのオプションの末尾にマイナス[-]を添えて該当行を反転させることができるようにした。例えば、":s/kato/d-"というコマンドの投入は、文字列"kato"を含まない行を削除することになる。これは文字列"kato"で grep したことと等価だ。他にもグローバルオプションをうまく組み合わせることで多様な処理を実現できる。例えば連続する空行を1行に集約する処理である。複雑なマクロを組むことなくこれを実現できるエディタに、私はお目にかかったことはない。WinViでは ":s/^$/U"の投入でこれを実現できる。もし空行に限らず連続する同一行をユニーク化したい場合は ":s/*/U" を投入すればよい。このように"/U"オプションは uniq 処理を行うことに他ならない。":s/*/Z" を実施すると、現在のウィンドウ右端で全行改行する。これは fold 処理に該当する。その他にも工夫次第で様々な一括処理が可能になるはずだ。
マクロ機構
テキストファイルの体裁を整える作業などで、何度も同じ操作を繰返す場合が多々ある。大概はグローバル処理や置換コマンドで対応できるが、カーソル移動を伴った微妙な修正の場合はそれらの活用が難しい。そのような局面で活躍するのがマクロ機構である。従来のviはマクロ記録の際、一連の操作を実際に行うスタイルが主流であるが、WinViではコマンド[=]にて機能文字列を記述する方式とした。一行バッチを作成するような感覚で気軽に入力でき、修正も容易である。文字として打ち込めない2つの特殊キー、[ENTER]と[ESC]に関しては、特殊文字"$"と"!"を準備した。特殊文字を通常文字として表現するためには"\"を添えて"\$"や"\!"として記述する。なお、一連のマクロ実行が終了した段階で編集モードに入っていた場合は、自動的に通常モードに復帰するため、最後の"!"は記述してもしなくても良い。マクロ実行はスペースキーであり、他の機能と同様に数字を添えて打鍵すると繰返回数も指定できる。例えば2行置きに"kato"という文字を6回挿入したい場合は、コマンド[=]で"Okato!3j"というマクロを登録し、6[SPACE]と打鍵すればよい。マクロはキーボードからの文字入力をそのまま展開する機構のため、多彩な組み合わせが可能である。ただし、コマンドへのトリガキー( / ? : , # = )やマクロ自体の実行[SPACE]など、一部の機能はスキップする仕様となっている。なおマクロ実行におけるアンドゥは、マクロコマンド発行単位で記録される。ヤンクバッファの入出力はマクロに記述された個々のコマンド実行を忠実にトレースして実施される。また、再現ピリオドはマクロ実行で更新されないため、マクロ実行直前に
セットされている再現ピリオドのコマンドをマクロ自体にピリオドで定義することが可能である。
特殊な置換文字のサポート
置換コマンド[:s]において置換側の文字列表記に特殊な文字を3つ装備した。ひとつは改行を表現する"$"で、適当な箇所に"$"を与えるとそこで行を折り返すことができる。もうひとつは連番を表現する"@"である。"@"部分には置換する度にインクリメントした数字が与えられる。連続した"@"でその桁数を与えることができ、上位桁はゼロで埋められる。例えば"@@@"と表記すると"001,002,003,…"と展開される。この連番を活用すると、テキスト内に存在するある予約語の出現数を確認したり、一過的に行番号を付与したり、ソート機構で利用するキーを行頭に付けたりすることができる。最後は検索文字列マッチングの展開を行う"&"のサポートである。一般の正規表現では、検索文字列側で部分文字列を()で囲むことでグループを定義し、置換文字列側でそのグループ順番に呼応した$1,$2,$3…を指定する方式だが、記述が煩わしく利用頻度も低い。考察してみるに、マッチング文字列展開の利用価値は『任意文字指定を活用する場合』にこそあることが見えてきた。そこで、検索文字列側の任意文字指定 . * [x]にマッチングした文字列を自動でグループ化し、その文字列を"&"で展開可能とするという処理を導入した。この仕様により検索文字列側にグループ定義は不要となる。なお、連続記述した . * [x]は1つのグループとして定義されるが、展開は初出のグループに限定しており、"&"を複数記述してもすべて同一の文字列が展開される。
全角に対応したワードジャンプ
ワードジャンプの課題は和文の対応だと考えた。英文は分かち書きが基本なのでシンプルなルールで実用的な動作を実現できるが、和文はベタに書き連ねるのでかなり複雑なルールを導入しないと精緻なワードジャンプができない。単純に、ひらがな、カタカナ、漢字、句読点、記号と細分化してしまうと、ジャンプ刻みが細かすぎてカーソル移動と同等となり意味を成さない。さりとて本格的に取り組むには構文に踏み込んだ解析が必要となるし、和文ルールを複雑にすると和英混合の場合は更に込み入った状況になる。しかるにそれほど使用頻度の高くないこの機能にあまり多大なプログラムコストを掛けたくなかった。そこで思い付いたのが「漢字とカタカナを同一種とみなし、これらが連続するものを単語とする」という素朴なルールである。こんなに荒いルールで本当に良いのか、と不安になる程シンプルだが、存外心地よく自然なジャンプをしてくれる。また、半角と全角のスペースは敢えて異なる種別として扱った。それらが混在して記述されていることを確認するのに便利だからである。一方、分かち書きのジャンプ[W][B]に関しては、半角と全角のスペースを同一に扱う。そして連続するスペースの末尾にカーソルが位置づけられるようにした。この仕様は一見奇矯に感じるかもしれないが、[w]で単語の先頭に位置づけた後、[W]で次の有意文字の直前にカーソルが移動するので、[ma][mx]との組み合わせ利用がしやすい。なお、[W][B]は[w][b]と異なり、行頭行末も停止位置候補となる。
長いカラム行への配慮
WinViは行の折り返し表示をサポートしていない。ウィンドウに収まりきらない文字列も一行で処理される。ウィンドウの幅に依存して文字のカラム位置が変化すると作業がし難いため、たとえ折り返しオプションが選べるエディタであっても、常に折り返し無しで作業しているという私自身の体験に基づいている。ただし、折り返し無しの制約を補間するためいくつかの機構をサポートした。1つはウィンドウからはみ出た長いカラムの行で[TAB]を押下すると行末までの内容がポップアップする機構である。その活用目的から連続するタブやスペースは1つに集約される。また、このウィンドウ内の文字列をクリップボードにコピーしたい場合は、選択文字列を右クリックする、あるいは[CTRL]+[C]の押下で実施される。2つ目の機構はウィンドウに収まっていない行にジャンプする機能[!]である。最下行にジャンプ先の行番号と、ウィンドウ端を越えたカラム数が:m《 -n 》の形式で表示される。このジャンプを一度実施するとその後編集やフォント切替えを行わない限り、ウィンドウの横方向ストレッチでダイナミックに《 n 》が表示されるようになる。この時のnは、ウィンドウ表示可能カラムと最長カラム行との差になる。3つ目の機構は現カーソル行をウィンドウ幅で分割する[Z]機能である。このコマンドはグローバルオプションでも駆動できるため、テキストファイル全体の行をウィンドウ幅で一気に揃えることができる。4つ目のサポートは、ダブルコーテーションの押下でウィンドウの最右端カラムにカーソルを移動させる機能だ。行の長さを揃えるため、禁則文字を意識しながら改行を入力する作業などが効率的に行える。
ファイルの巡回
WindowsはOSそのものがマルチタスク、マルチウィンドウの機構を実現しているのであるから、単独のアプリケーション内で複数のデータを展開する必要はなく、素直にアプリケーション自体を複数起動すれば良いのだ、というのが持論である。しかし、WinViのロードファイルパスにはワイルドカードや列挙記述が使用できるため、必然的に複数ファイルを読込めることになる。そうなるとこれらのファイルを素早く切り替えるための機構が欲しくなる。そこで、一度読込んだファイルのパスは内部の巡回リストに累積登録され、[e][E]コマンドで簡便にファイルを切替えることができるようにした。2度読みしてもリスト内で重複させない工夫も施している。切替えタイミングで表示ページの位置も復元されるため、巡回しながら特定ページの比較もしやすくなっている。また編集を施したデータは、安易な切替えで編集情報を失わないようガードしているが、その時点でセーブをするか[^E]で強制的に再読込みを実施すれば巡回を継続できるようにした。こうして構築された巡回リストの中から、特定の1ファイルを除去する機能もサポートした。[^Q]の押下で現在読込まれているファイルがリストから除去され、次のファイルが読込まれる。この機能も編集済みのチェックが掛かる様にした
コマンド系の履歴
コマンド[:]、検索[/?]、マクロ[=]の3つの実行履歴が独立してWinVi起動直後から記録される。そして、各モードに入った状態で[↓][↑]を押下することで履歴をトレースすることができる。ホームポジションから手を離さず操作を可能にするため、[^K][^J]でも同じ動作をする様にした。また、コマンド[:]の履歴は使用頻度が高いことを想定し、直近履歴を表示してコマンドモードに移行するカンマ[,]を設けた。動作は[:][↓]の連続押下と等価であるが、同じコマンドを何度も実行したい場合にホームポジションから手を離すこと無く実行できる。なお、コマンドエリアではマウスによる選択を含めたWindows標準の各種キー操作が可能である。( [^C]コピー [^V]貼付け[^X]切取り [^Z]元に戻す [←][→]カーソル移動 など )。また微々たる工夫ではあるが、コマンド入力時点の[ESC]の挙動をマクロ[=]とそれ以外[:/?]で変えてある。後者は[ESC]の押下で即座に通常モードに戻るが、前者は一旦文頭に復帰した後、再度[ESC]押下することで通常モードに戻る。前回記録したマクロをクリアして新たにマクロを定義し直す際に便利である。
マウスホイールによる可変ピッチスクロール
マウスホイールによるスクロールは軽快で負担のない操作感を得られる。しかし一般的にはスクロールピッチ、つまり1ノッチ当たりに移動するスクロール行数が固定的であるため、素早く高速にスクロールしたい場合と望むべきページ表示範囲に精緻に調整したい場合の切り分けが難しい。そこで固定ピッチと可変ピッチのモードを、マウスのホイールボタンでトグル切替え可能とする機構を導入した。固定ピッチは1行単位のスクロールであるが、今回新設した可変ピッチに切替えるとマウスカーソルの行位置に応じてスクロールピッチが変化する様になる。可変ピッチは、表示行の上部にマウスカーソルを位置づけてホイールを回すと、移動量が小さく穏やかにスクロールする。逆に下部にマウスカーソルを位置づけてホイールを回すと移動量が大きく素早くスクロールする。現在マウスカーソルが位置づけられている行と先頭行との差分で、スクロールピッチを決定する動作原理である。これにより、ラフな高速スクロールと、精緻な位置決めスクロールとをシームレスに両立させた操作が可能となる。
閲覧エリアを示す階層ゲージ
可変型のつまみを持ったスクロールバーは、現在の表示位置や表示比率が俯瞰でき美しいと感じている。しかしキーボードのホームポジションから手が離れるマウス操作は極力排除したい。そこで、状態をモニタするだけでマウス操作不能なスクロールバーを右端に付けてみた。更に、エディタでモニタすべき要素を考察すると、全体に対する表示ページ範囲と、ページ内でのカーソル位置という2つの要素があることが見えてきた。そこで表示ページ内でのカーソル位置を赤いマークで示すという階層型のゲージをサポートした。カーソル移動やページのスクロールに応じて動く2階層のゲージは、見ていてちょっと楽しい。
タブカラムの概念を持つソーティング
リスト形式のデータを編集する際に有効なソート機構をサポートした。[:h]で順ソート、[:h-]で逆ソートとなる。行範囲の指定も可能なので部分的な行範囲のソートも可能だ。置換コマンドで連番挿入したり、グローバルコマンドで特定行頭に文字挿入すると、様々なタイプのソートを実現できる。更にhに続いてタブカラム数を指定すると、行の途中からソート比較対象を設定できる。タブカラムとは連続するタブを1つのデリミッタとカウントする列指定である。例えば、[:h2]と指定すると、“Mr.(タブ群1)Kato(タブ群2)Ichiro”という文字列の“Ichiro”以降をソート比較対象にすることができる。デフォルトは行の先頭から比較しているため[:h0]と解釈できる。また、[:h10000]などとして、全行とも明らかに末尾まで比較対象から外れる様な指定をすると、クイックソートの特性から全行の順番を一気に反転させることもできる。なお、ソーティングのタイプは、[:h]と[:H]の2系統をサポートしている。前者はロケールによるソート、後者はコードによるソートである。例えば半角“12abAB”と全角“12abAB”が存在する時、[:h]は“1122aaAAbbBB”とソートされ、[:H]は“12ABab12ABab”とソートされる。
その他の特徴
検索を繰り返す[n]と[N]の動作定義を変更した。従来のviは[n]で検索方向を維持し、[N]で検索方向を反対にする。つまり投入した検索コマンド[/]や[?]と従属関係にある。WinViではこの従属を断ち切り、あくまでも[n]は前方への検索、[N]は後方への検索とした。また[^N]で、検索文字列の入力による検索開始時点の行にジャンプし、作業基点へ復帰を可能とした。また、:1 :$ で先頭行や末尾行に直接ジャンプする際も、ジャンプ直前の行を同一機構で記憶し、逆に :1 :$ からの検索時には記憶しないようにした。これにより、先頭行や末尾行に一旦移動してから検索を実施した場合も、[^N]で本来の作業基点に復帰できる。
括弧対のジャンプ[%]にも小さな工夫を施した。従来のviはカーソルを括弧に位置づけてからの発行となるが、WinViではどの場所からでも前方向近傍の括弧を探し出し、その後括弧対にトグルでジャンプする。括弧対は ( ) { } [ ] に加えて < > にも対応することにした。拙作音楽ソフトMuseでのオクターブ復帰確認に威力を発揮する。なお、本機能が主にコーディングのチェック時に使用されることを勘案し、敢えて全角の括弧対は処理対象から外した。
WinViは私自身のプログラム開発における中心的な道具である。よって関数ヘッダー部へのジャンプはぜひ欲しかった。そこで /**- という4文字で始まる行を対象にし、"["および"]"キーでジャンプさせることにした。固定的仕様で非標準のルールではあるが、関数仕様書を捲るが如く表示が切替わり使い勝手が良い。
フォント選択は[\]の押下あるいはマウス右クリックでポップするフォントリストから可能である。1階層目には等幅フォントが、2階層目にはプロポーショナルフォントが展開される。また、現選択フォントにはラジオマークが付与される。フォントサイズの変更は { } キーの押下、あるいは[CTRL]を併用したマウスホイールで連続的に実施可能だ。
カーソルのキーアサインは“編集”ではなく“閲覧”であるという思想で設計した。[↓][↑]をスクロールとし、[SHIFT]と組合わせてページ移動とした。[↓][↑]をカーソル移動にしなかったのは、キー押下をした時点で即座に表示が移動する方が閲覧効率が高いからだ。閲覧という思想に基づき[←][→]はファイル切替えをアサインした。なお、通常および絞込みモードでは[↓][↑]はスクロールであるが、コマンドモードでは履歴トレースとして働く。
[CTRL]併用の矢印キーでスクリーン四辺端にウィンドウを寄せる。更にその矢印キーを押下したまま、直行する矢印キーの追加押下で、四隅に寄ったウィンドウとなる。また、[CTRL]+[W]にてウィンドウを最大化し、再度押下する事で通常に戻る。これらウィンドウサイズ変更の割込みは、あらゆるモードで実施可能である。
[CTRL]+[T]にて、ウィンドウを常に手前にすることができる。再度発行すると通常モードに戻る。モードが切替わる際に、ウィンドウの左下に▲/▽マークが表示される。