Word VBAの深淵へ:段落の「差異」を可視化する究極のデバッグ術
こんにちは。自動化の世界へようこそ。
マクロの記録で生成された「冗長で壊れやすいコード」に別れを告げ、Wordのドキュメント構造を意のままに操るエンジニアの扉を叩いたあなたに、今日は一段深い話を用意しました。
ドキュメントの品質管理において、最も頭を悩ませるのが「見た目は似ているのに、なぜか書式が崩れる」という現象です。これを解決するのは、目視ではありません。プロパティ単位での「差分解析」です。
今日は、2つの段落オブジェクトを比較し、どこが違うのかを論理的に抽出するプロフェッショナルなロジックを伝授します。
—
1. なぜ「書式設定」の比較が難しいのか?
Wordの段落(`Paragraph`)は、内部的に`Range`、`Font`、`ParagraphFormat`、そして`Style`という複雑なレイヤーで構成されています。
初心者が陥りやすい罠は、「スタイル名が同じなら中身も同じはずだ」と思い込むこと。しかし、Wordでは「直接書式(スタイル適用後に手動でフォントサイズを変えるなど)」が混ざることで、見た目とプロパティが乖離することがあります。
我々エンジニアがやるべきことは、「どのプロパティが、どの値で食い違っているのか」を数値で突き止めることです。
—
2. 差分解析エンジンの実装
以下のコードは、二つの段落を比較し、不一致項目をイミディエイトウィンドウに出力する比較ロジックです。
Option Explicit
‘ — 段落の書式差異を解析するプロフェッショナル・ロジック —
Public Sub CompareParagraphFormats(p1 As Paragraph, p2 As Paragraph)
Debug.Print “— 比較開始: ” & Now & ” —”
‘ 1. スタイルの不一致チェック
If p1.Style <> p2.Style Then
Debug.Print “【不一致】Style: ” & p1.Style & ” vs ” & p2.Style
End If
‘ 2. Fontプロパティの深層比較
CompareProperty “Font.Name”, p1.Range.Font.Name, p2.Range.Font.Name
CompareProperty “Font.Size”, p1.Range.Font.Size, p2.Range.Font.Size
CompareProperty “Font.Bold”, p1.Range.Font.Bold, p2.Range.Font.Bold
‘ 3. 段落フォーマット(インデント・行間)の比較
CompareProperty “ParagraphFormat.LeftIndent”, p1.Format.LeftIndent, p2.Format.LeftIndent
CompareProperty “ParagraphFormat.LineSpacing”, p1.Format.LineSpacing, p2.Format.LineSpacing
CompareProperty “ParagraphFormat.Alignment”, p1.Format.Alignment, p2.Format.Alignment
Debug.Print “— 比較終了 —”
End Sub
‘ 差分を判定してログに出力する共通関数
Private Sub CompareProperty(propName As String, val1 As Variant, val2 As Variant)
If val1 <> val2 Then
Debug.Print “【不一致】” & propName & “: ” & val1 & ” -> ” & val2
End If
End Sub
コードの重要ポイント
- Variant型の活用: プロパティには数値も文字列も存在するため、`Variant`で受け取るのが定石です。
- 比較関数(CompareProperty)の分離: ロジックを切り出すことで、比較項目が100個に増えてもメインコードが汚れません。保守性の高さこそが、プロとアマの差です。
—
3. 陥りやすいエラーと回避策
① `Range`の参照範囲に注意せよ
`Paragraph.Range`には、段落記号も含まれます。もし段落内のテキストの一部だけを比較したい場合は、`Paragraph.Range.Characters`をループさせる必要がありますが、まずは「段落全体の属性」を揃えることが品質安定化の第一歩です。
② `wdUndefined`(未定義)の罠
Word VBAには、設定が混在している(一部は太字、一部は標準など)場合に `999999` (wdUndefined) を返すプロパティがあります。単純に `If val1 <> val2` と比較すると、予期せぬ挙動をすることがあります。
対策: 厳密な比較を行う際は `If val1 <> val2 And val1 <> wdUndefined Then …` といったガードを入れましょう。
—
最後に:自動化の先にある世界
このコードを応用すれば、「校正用ドキュメント」と「本番ドキュメント」の段落を走査し、食い違いがある箇所を赤色にハイライトする自動校正ツールさえ作成可能です。
「マクロの記録」ボタンを押して終わる段階はもう卒業です。Wordのオブジェクト構造を掌握し、自分が意図した通りに文書を制御する。その感覚を一度掴めば、業務自動化は「単なる作業」から「知的生産」へと変わります。
ここをクリアしたあなたは、もう立派なWord VBAエンジニアです。次回の記事では、この比較ロジックをさらに発展させ、ドキュメント全体を巡回する「再帰的解析エンジン」についてお話ししましょう。
何か不明点があれば、遠慮なく聞いてくださいね。一緒に最高峰の自動化環境を構築しましょう。
