はじめに
ソースコードを書いている開発時には、いろいろなバージョンのファイルができあがるため、両者間の差分を取って変更箇所を確かめたいということがよくあります。しかしながら、Visual Studio .NETのIDE環境において、標準のメニューコマンドには、この機能が見当たりません。
通常、このようなケースでは「diff」という、Unix環境では定番のツールを使用します(Win32版の「diff.exe」もあります)。Windowsでは、これを模した「WinDiff」というGUIツールが、Visual StudioやResource Kitなどに付属しています。
しかし、これらを使うには、その都度、
- デスクトップに戻って、
- アプリケーションを起動し、
- 比較するファイルを選択する
というような作業を繰り返さなければならず、かなり面倒です。
この問題を楽にするための小さなVisual Studio .NETマクロを紹介します。
対象読者
Visual Studio 2002以上を対象にしています。
必要な環境
Visual Studio 2002が必要です。2003では検証していませんが、大丈夫と思います。
マクロとは
マクロは操作の手順を記述して、定型作業を自動化するための機能です。ExcelのVBAなどと同様、Visual StudioにもVBAのようなものがついています。ただし、Visual Studioの場合、Visual Basic.NETで記述します。
今回作成するマクロの概要
WinDiffはGUIツールですが、コマンドプロンプトから起動できます。2つのファイルを比較する場合、起動オプションとして、比較する2つのファイルパスを与えてやるだけです。この例では「C:\WinDiff.Exe」というパスにインストールされていると想定します。
>C:\WinDiff.exe "c:\file1.txt" "c:\file2.txt"
このことから、マクロの設計としては、以下のようになります。
- ソリューションエクスプローラで選択中の2つのファイルパス情報を取得
- 2つのファイルパスを引数としたコマンド文字列を作成し「WinDiff.exe」のプロセスを起動する
準備
[ツール]→[マクロ]→[マクロIDE...]を実行し、マクロIDEを起動します。プロジェクトエクスプローラから「MyMacros」を右クリックし、[追加]→[モジュールの追加]をクリックしてモジュールを追加します。「Public Module ~」というセクションが既に記述済みなので、この中にマクロのルーチンを書きます。
マクロの実装
まず、VSマクロでは「DTE(Development Tools Extensibility)」というIDE環境を拡張するためのグローバルなオブジェクトが用意されており、このオブジェクトをツリー上にたどっていくことで、開発環境に存在する膨大なオブジェクトを操作することができます。
コードのポイントですが、まず、ソリューションエクスプローラで選択したファイルやフォルダの情報を取得するには、DTE
オブジェクトのSelectedItems
プロパティを使います。
あとは取得したものをFor Each
でループして、項目がProjectItem
オブジェクトである場合、FileNames(1)
で完全パスを参照できます。プロパティが配列型になっているのは、選択しているプロジェクトの項目によっては、関連付けられているファイルが複数になることもあるためです。ただ、ほとんどの場合は、1つのプロジェクト項目に対して1つのファイルです。
ファイル名を取得できたら、あとはコマンド文字列を作成し、System.Diagnostics.Process
を使ってプロセスを起動するだけです。
Sub Windiff_CompareFiles() '実行パスは個人の各環境に応じて書き換えてください。 Dim diffPath As String = "C:\Program Files\Tools\Bin\WinDiff.Exe" Dim SelItem As SelectedItem Dim argStr As String '2つのアイテムが選択されていることの確認 If (DTE.SelectedItems.Count <> 2) Then Exit Sub For Each SelItem In DTE.SelectedItems 'プロジェクト内のアイテムなら処理する If (Not SelItem.ProjectItem Is Nothing) Then argStr = argStr + """" _ + SelItem.ProjectItem.FileNames(1) + """ " End If Next Dim proc As System.Diagnostics.Process _ = New System.Diagnostics.Process() proc.StartInfo.FileName = diffPath proc.StartInfo.Arguments = argStr proc.StartInfo.WindowStyle = ProcessWindowStyle.Normal proc.Start() End Sub
ツールバーへの登録
マクロを作ったらツールバーへ登録しましょう。これで、2つのファイルを選択して、ツールバーからボタンをクリックすればWinDiffが比較を実行してくれます。
DF
ところで、WinDiffもなかなかよいのですが、より高機能で使いやすい「DF」というすばらしいフリーソフトをここでは取り上げることにします。このツールもWinDiff同様、比較する際は2つのファイルパスを引数にとりますから、実行パスをこのDFをインストールした場所に書き換えれば、上記のマクロをそのまま使用することができます。
おわりに
Visual Studioにはマクロ機能がついています。寡聞にしてVSのマクロをバリバリ活用しているという噂を余り聞かないのですが、意外と(?)使いものになります。あるものを使わないのももったいないので、アイデア次第でいろいろと活用して、CodeZineにもそのアイデアを投稿してください!