MS Project VBAの深淵:依存関係による「ガントチャートの動的ビジュアライズ」を極める
多くのエンジニアがMS ProjectのVBAを触り始めると、まず陥る罠がある。それは「オブジェクトのプロパティを片っ端から直接叩く」という素人仕事だ。
プロジェクトの規模が大きくなればなるほど、依存関係(FS, SS, FF, SF)が複雑化し、手動でガントチャートのバーを管理するのは不可能に近い。かといって、VBAで闇雲に描画制御を行えば、Projectの計算エンジンと競合し、パフォーマンスは一気に劣化する。
今日は、プロフェッショナルとして「なぜ依存関係に基づいた動的なスタイル変更が必要なのか」、そして「それをいかに堅牢に実装するか」を伝授する。
—
1. なぜ「ハードコーディング」は死を招くのか
よく見かけるのは、`Task.BarStyles` をベタ書きで操作するコードだ。これはメンテナンス性の観点から「罪」に近い。
- 競合のリスク: MS Projectには強力なスケジューリングエンジンがある。VBAで強引に色を変えても、再計算のたびに設定が上書きされる可能性がある。
- イベントループの弊害: `Project_Change` イベントで毎回全タスクを走査すれば、数千行のプロジェクトでは数秒のフリーズが確定する。
極限の解法:
「依存関係の種類」というメタデータをトリガーに、BarStylesそのものを変更するのではなく、「Custom Field(フラグや文字列)」を介した条件付き書式に近い運用を行うことだ。これが最もProjectのカーネルに負荷をかけず、かつ保守性に優れたアプローチとなる。
—
2. 実装の設計思想:依存関係を「可視化の引数」にする
今回は、先行タスクとのリンク関係(LinkType)を判定し、特定の色と形状を動的に割り当てるアーキテクチャを構築する。
実装のポイント
1. 直接操作の回避: プロパティを直接いじるのではなく、専用のCustom Field(例: `Text1`)に属性を書き込み、Project側で「バーのスタイル」設定をそのフィールドに依存させる。
2. イベントの最適化: 全タスクをループさせるのは愚策。変更されたタスクの先行タスク(Predecessors)のみを射抜くアルゴリズムを採用する。
—
3. プロダクションコード:動的スタイリング・エンジン
このコードは、依存関係のタイプに応じてプロジェクトの視認性を劇的に向上させる。
‘ 依存関係に基づき、タスクの可視化属性を更新するコアロジック
Public Sub ApplyDependencyStyle(ByVal t As Task)
Dim pred As TaskDependency
Dim styleTag As String
‘ エラーハンドリング:依存関係がない場合は終了
If t.TaskDependencies.Count = 0 Then Exit Sub
‘ ここでは「最も影響力の強いリンク」をロジックで抽出する
‘ FS(Finish-to-Start)であれば標準、SS(Start-to-Start)であれば警告色など
For Each pred In t.TaskDependencies
Select Case pred.LinkType
Case pjFinishToStart
styleTag = “FS_NORMAL”
Case pjStartToStart
styleTag = “SS_PARALLEL” ‘ 並行作業は視覚的に目立たせる
Case Else
styleTag = “OTHER”
End Select
Next pred
‘ 直接描画するのではなく、データベース(Custom Field)に状態を書き込む
‘ このText1をベースに、ガントチャートのバー設定で色分けを行うのが鉄則
t.Text1 = styleTag
End Sub
‘ 一括更新時のパフォーマンスを最大化するラッパー
Public Sub RefreshProjectStyles()
Dim t As Task
‘ 画面描画を停止してCPUリソースを確保
Application.ScreenUpdating = False
For Each t In ActiveProject.Tasks
If Not t Is Nothing Then
ApplyDependencyStyle t
End If
Next t
Application.ScreenUpdating = True
End Sub
—
4. プロの現場で生き残るための「注意点」
1. 描画設定の「外部化」
上記のコードで `t.Text1` に値を書き込んだだけでは何も起きない。必ずMS Projectの「ガントチャートバーの書式設定」を開き、「条件付きバー」としてText1の値が “SS_PARALLEL” の時に色を赤にするという設定を保存しておくこと。これが「VBAとGUIのハイブリッドによる堅牢性」だ。
2. ファイル連携の罠
外部のExcelやSQL Serverからタスクをインポートする場合、依存関係のID(Unique ID)とリンクタイプを必ず整合させること。インポート後に一度 `RefreshProjectStyles` を呼ぶフローを自動化ツールに組み込むのが、バグを未然に防ぐ唯一の道だ。
3. パフォーマンスの限界
数万タスクを超えるプロジェクトでは、`For Each` ループすら重荷になる。その場合は `Task.ID` を配列に格納し、メモリ上で処理してから一括で書き戻す `Variant` 配列演算を取り入れる必要がある。これについては、また別の機会に深く語るとしよう。
—
最後に:エンジニアへのメッセージ
VBAは単なる「自動化のためのスクリプト」ではない。Projectの堅牢なスケジューリング・エンジンをハックし、プロジェクトマネージャーの意思決定を支援する「知的な拡張機能」であるべきだ。
コードを書く前に、「Projectの標準機能で代替できないか?」を常に自問せよ。それができる者だけが、真に保守性の高い自動化システムを構築できる。
健闘を祈る。
