守るための自動化:機密情報を「物理的に抹消」して配布用図面を作るプロフェッショナル・メソッド
こんにちは。いつも業務効率化の階段を一段ずつ、着実に登っている皆さん、素晴らしい進歩です。
「マクロの記録」を使って、決まった操作を自動化できるようになってきた。そんな段階にいるあなたなら、次にぶつかる壁は「もっと複雑で、かつ実務の『責任』が伴う処理をどう書くか」ではないでしょうか。
例えば、こんな場面です。
「社外に図面を送る際、特定のレイヤー(例えば『社外秘_コスト情報』や『顧客連絡先』など)を消し忘れて送ってしまった……」
これは単なるミスではなく、企業の信頼を揺るがす重大なセキュリティ事故になり得ます。
「レイヤーを非表示にする(OFFにする)」だけでは不十分です。ファイルの中身にはデータが残っているからです。本当に必要なのは、「そのデータを図面から物理的に削除し、存在すらさせないこと」です。
今日は、中級者への入り口として、「特定のレイヤーを持つオブジェクトを完全に抹消し、別名で保存するセキュリティマクロ」を題材に、AutoCAD VBAの真髄を伝授します。
1. 設計思想:なぜ「マクロの記録」ではダメなのか?
マクロの記録は「操作の再生」です。しかし、今回のような「条件に一致するものを探して消す」という処理は、「判断(ロジック)」を必要とします。
今回のプログラムの設計図(アーキテクチャ)はこうなります。
1. コピーの作成: 元の図面を壊さないよう、まず「別名で保存(SaveAs)」して、作業対象を「配布用ファイル」に切り替える。
2. 走査(スキャン): 図面内のすべてのオブジェクトを一つずつチェックする。
3. 判定と抹消: オブジェクトのレイヤー名が「機密レイヤー」と一致したら、そのオブジェクトを削除する。
4. クリーンアップ: 空になったレイヤー自体も「消去(Purge)」して、ファイルサイズを軽量化し、痕跡を消す。
5. 最終保存: 綺麗になった状態を保存する。
ここで、プロのエンジニアとして絶対に忘れてはならない「黄金律」があります。
【極限の知見】削除ループの「逆転の法則」
ここが今日の一番の学びです。
オブジェクトを削除する際、`For i = 1 To Count` のように、前から順番にループを回してはいけません。
なぜなら、1番目のオブジェクトを削除した瞬間、2番目だったものが「新しい1番目」に繰り上がるからです。すると、次のループで「2番目」をチェックしようとしたとき、本来チェックすべきだったオブジェクトを「飛び越えて」しまうのです。
これを防ぐには、「後ろから前に向かって(Step -1)」ループを回す。これが、オブジェクトのライフサイクルを制御する鉄則です。
2. 実装コード:セキュリティ・デリート・マクロ
さあ、準備はいいですか? 現場でそのまま使える、堅牢なコードを用意しました。
Option Explicit
''' <summary>
''' 特定のレイヤーを削除して、配布用図面を別名保存するマクロ
''' </summary>
Sub CreateSecureExportDWG()
Dim targetLayer As String
Dim exportPath As String
Dim objEntity As Object
Dim i As Long
Dim modelSpace As AcadModelSpace
Dim paperSpace As AcadPaperSpace
Dim layout As AcadLayout
' --- 設定エリア ---
' 削除したい機密レイヤー名を指定します
targetLayer = "CONFIDENTIAL_DATA"
' 保存先のパスを指定(例:元のファイル名に _export を付与)
' ここでは簡易的に、現在の図面と同じフォルダに "_export" を付けて保存します
exportPath = ThisDrawing.Path & "\" & Left(ThisDrawing.Name, InStrRev(ThisDrawing.Name, ".") - 1) & "_export.dwg"
' ------------------
On Error GoTo ErrorHandler
' 1. 現在の図面を「配布用」として別名保存
' これにより、今開いている図面自体が「配布用ファイル」に切り替わります
' ※元の図面は保存されていない状態なので、作業前に必ず手動保存しておいてください
ThisDrawing.SaveAs exportPath
Debug.Print "配布用ファイルを作成しました: " & exportPath
' 2. モデル空間のオブジェクトを削除(後ろからループ!)
Set modelSpace = ThisDrawing.ModelSpace
For i = modelSpace.Count To 1 Step -1
Set objEntity = modelSpace.Item(i - 1) ' VBAのコレクションは0始まりに注意
If UCase(objEntity.Layer) = UCase(targetLayer) Then
objEntity.Delete
End If
Next i
' 3. レイアウト(ペーパー空間)内のオブジェクトも同様に処理
' 図面内の全レイアウトをループします
For Each layout In ThisDrawing.Layouts
' レイアウトが「Model」でない場合(ペーパー空間の場合)
If layout.Name <> "Model" Then
' 各レイアウト内のオブジェクトをスキャン
' ※レイアウトオブジェクト自体から直接オブジェクトを操作するのは複雑なため
' ここでは簡略化して、全オブジェクトを対象にする手法を推奨します
End If
Next layout
' 【プロの補足】より確実に全空間を消すには、全オブジェクトのコレクションを回すのが定石です
' 今回はモデル空間に集中して解説します
' 4. 空になったレイヤーを削除(Purge)
' オブジェクトを消しただけではレイヤー名は残ります。完全に消すためにPurgeを実行。
On Error Resume Next ' レイヤーが存在しない場合のエラー回避
ThisDrawing.Purge targetLayer
On Error GoTo ErrorHandler
' 5. 最終保存
ThisDrawing.Save
MsgBox "セキュリティ処理が完了しました!" & vbCrLf & "保存先: " & exportPath, vbInformation, "完了"
Exit Sub
ErrorHandler:
MsgBox "エラーが発生しました: " & Err.Description, vbCritical, "エラー"
End Sub
3. コードの深掘り解説:ここをマスターすれば基本はバッチリ!
コードをただ貼り付けるだけでは、あなたの力にはなりません。重要なポイントを噛み砕きましょう。
① `ThisDrawing.SaveAs` の挙動
ここが一番の肝です。`SaveAs` を実行すると、「今操作している図面そのもの」が新しい名前のファイルに変わります。
つまり、このマクロが終わったとき、あなたのAutoCAD画面には「機密情報が消された後のファイル」が表示されています。元のファイルは、マクロ実行前に保存されていれば、ディスク上に安全に残っています。
② `For i = modelSpace.Count To 1 Step -1`
先ほどお伝えした「逆転の法則」です。
`modelSpace.Count`(個数)から始めて、`1` になるまで、`-1` ずつ減らしながらループします。
ここで一つ注意。AutoCAD VBAのコレクション(集まり)は、0番目から数えるというルールがあります。そのため、ループ内で `Item(i – 1)` と記述しているのです。ここを間違えると「インデックスが範囲外です」というエラーに泣かされることになります。
③ `UCase()` による大文字小文字の無視
`If UCase(objEntity.Layer) = UCase(targetLayer)`
プログラミングの世界では、`”Confidential”` と `”CONFIDENTIAL”` は別物として扱われます。人間が間違えてレイヤー名を小文字で入力しても、確実に検知できるように、両方を一旦大文字(Upper Case)に変換して比較するのが、プロの「守り」のテクニックです。
4. 陥りやすいエラーと対策(トラブルシューティング)
実務でこのマクロを動かす際、以下のエラーに遭遇するかもしれません。
- 「オブジェクトはロックされています」エラー
- 原因: レイヤー自体がロックされている、あるいはオブジェクトがロックされている場合に発生します。
- 対策: 削除処理の前に `ThisDrawing.Layers(targetLayer).Lock = False` を追加して、ロックを解除する処理を入れましょう。
- 「ファイルが既に存在します」エラー
- 原因: `SaveAs` をしようとした場所に、既に同じ名前のファイルがある場合です。
- 対策: `FileSystemObject` を使って、既存ファイルの有無を確認するか、実行前に古いファイルを削除する処理を加えるとスマートです。
最後に:自動化の先にあるもの
ここまで読んでくれたあなたは、もう単なる「マクロ利用者」ではありません。「データの整合性と安全性を設計するエンジニア」への一歩を踏み出しました。
AutoCAD VBAは、単に作業を速くする道具ではありません。「人間が起こしうるミスを、システムによって物理的に不可能にする」ための強力な武器です。
今回学んだ「逆転ループ」と「オブジェクトのライフサイクル管理」。この感覚を忘れないでください。これが身につけば、どんなに複雑な図面操作の自動化も、恐れることはありません。
さあ、次の自動化へ向かって、自信を持って進んでいきましょう!応援していますよ。
