AutoCAD VBAを掌握する:単位混在入力(フィート・インチ)を「真の数値」へ変換する極意
AutoCADの自動化において、最も泥臭く、かつ最も軽視されがちなのが「ユーザーインターフェースの入力制御」だ。
君たちが書くマクロで、ユーザーに数値を入力させる際、`InputBox` を使って単純な `Double` を期待していないだろうか? もしそうなら、君のツールは「現場の職人」には一生使われない。現場は `100` と打ちたい時もあれば、図面に合わせて `1’6″` や `12.5cm` と打ちたいのだ。
今日は、AutoCADのAPIが標準で備える強力な武器 `Utility.DistanceToReal` を使い、どんな単位表記も計算可能な `Double` に叩き込む「堅牢な変換ロジック」を伝授する。
—
なぜ自作のパース関数を書いてはいけないのか?
初心者ほど、「文字列から `’` や `”` を探して計算する」という愚かな正規表現ロジックを組みたがる。しかし、AutoCADにはOSの地域設定や図面単位に依存せず、正確に値を解釈するエンジンが既に組み込まれている。
それが `Utility.DistanceToReal` だ。このメソッドを使いこなすことこそ、AutoCAD APIの本質を理解している証明になる。
—
実装:堅牢な入力解析モジュール
以下のコードは、単に変換するだけではない。「ユーザーの入力キャンセル」や「不正なフォーマット」を適切にハンドリングし、後続の計算処理を止めないためのプロダクション・レベルの設計だ。
Option Explicit
”’
”’
”’ コマンドラインに表示するメッセージ
”’
Public Function GetRealFromUserInput(ByVal prompt As String) As Double
Dim util As AcadUtility
Set util = ThisDrawing.Utility
Dim inputStr As String
Dim resultValue As Double
On Error Resume Next ‘ ユーザーのキャンセル(ESC)をトラップするため
‘ 1. コマンドラインからの入力を受け取る
inputStr = util.GetString(True, vbCrLf & prompt & ” > “)
If Err.Number <> 0 Then
‘ ESCキーなどで中断された場合
GetRealFromUserInput = -1
Exit Function
End If
On Error GoTo 0
‘ 2. DistanceToRealによる変換
‘ acDecimal: 変換後の単位系を十進数に指定
On Error Resume Next
resultValue = util.DistanceToReal(inputStr, acDecimal)
If Err.Number <> 0 Then
MsgBox “入力値が不正です。単位形式を確認してください。”, vbCritical
GetRealFromUserInput = -1
Else
GetRealFromUserInput = resultValue
End If
On Error GoTo 0
End Function
—
この設計が「プロ」である理由
1. `acDecimal` の指定が運命を分ける
`DistanceToReal` の第二引数に `acDecimal` を指定することで、AutoCADは入力を「現在の図面の単位設定(LUNITS)」に関わらず、数学的な数値として解釈する。これにより、フィート・インチ表記であっても、図面単位がメートル法であっても、常に期待通りのミリメートル単位(またはベース単位)の `Double` が返ってくる。
2. `On Error Resume Next` の正しい使い所
VBAにおいてエラー制御は忌避されがちだが、CADの入力を扱う場合、`Utility.GetString` はユーザーのESC操作で即座にランタイムエラーを投げる。これを「例外」としてではなく「操作フローの一部」として扱うのが、エンジニアリングとしての正解だ。
3. ファイル・データベース連携への布石
もし君がこの数値をデータベースに保存する場合、絶対に文字列のまま保存してはいけない。この関数で `Double` に変換し、計算値として保持せよ。データベース側では、単位変換はあくまで「表示層」の仕事であるべきだ。ロジック層は常に「純粋な数値」のみを扱う。これが、後々「インチからメートルへの変換機能追加」といった仕様変更に耐える唯一の設計だ。
—
チーフアーキテクトからの助言:入力の抽象化
実務の現場では、この関数をさらにラップし、`UserInputManager` のようなクラスモジュールに昇華させることを強く推奨する。
- 入力履歴の保持: ユーザーが前回入力した値をデフォルト値として提示する。
- バリデーション: `resultValue <= 0` の場合にエラーを投げるのではなく、再入力を促すループ処理を組み込む。
「ただ動くもの」を作るのはエンジニアの卵だ。「どんな入力が来てもシステムをクラッシュさせず、かつ現場の思考を止めないツール」を作ること。それが、AutoCAD VBAを極めるということだ。
さあ、君のコードを書き直せ。今日のコードは、明日の君の工数を劇的に減らすはずだ。
