為了保護 VBA 程式碼不被輕易破解,並提升執行速度,我們可以將 VBA 專案編譯封裝成 DLL 動態連結庫,再由 Word 呼叫。本文詳細說明從建立 VB 專案、修改程式碼差異、封裝使用者表單,到在 Word 中引用 DLL 的完整流程。
VBA 程式碼以原始碼形式儲存在文件中,容易被檢視與修改。透過 Visual Basic 6.0 編譯為 DLL,程式碼將轉為機器碼,不僅難以逆向工程,執行效率也會顯著提升。
VBAPrj,類別模組名稱改為 VBACls。Test)複製貼上至 VB 的類別模組 VBACls 中,使其成為類別的方法。VBAPrj.dll 檔案。VBA 與 VB 6.0 雖同源但有差異,需對移植的程式碼做必要修改:
如 Document、Range、Bookmark 等物件,VB 無法辨識。解決方法:將這些物件作為參數傳遞,參數型別統一設為 Object。
範例:原 Sub Test() 需存取 ThisDocument,改為 Sub Test(Doc As Object),呼叫時傳入 ThisDocument。
如 ProtectType 等常數,VB 也不認得。同樣改為參數傳遞,型別設為 Variant。
例如 wdNoProtection 是 Word 專有常數。可在 Word 的立即執行視窗輸入 MsgBox CStr(wdNoProtection) 取得其數值(如 -1),再將程式碼中的常數直接替換為數值。
.frm 檔。.frm,表單與其程式碼將一併匯入。假設已產生 VBAPrj.dll,包含類別 VBACls 與方法 Test(Doc As Object),提供三種引用方式:
Dim VBACls As New VBAPrj.VBACls
VBACls.Test(ThisDocument)
Private Sub Document_Open()
On Error Resume Next
Me.VBProject.References.AddFromFile "D:\VBAPrj.dll"
End Sub
Private Function GetProjectDoc() As Object
On Error Resume Next
Dim VBACls As Object
Set VBACls = CreateObject("VBAPrj.VBACls")
If VBACls Is Nothing Then
MsgBox "VBAPrj.dll 必須與文件在同一目錄下!"
Exit Function
End If
Set GetProjectDoc = VBACls
End Function
' 呼叫範例
Dim objPrjDoc As Object
Set objPrjDoc = GetProjectDoc
Call objPrjDoc.Test(ThisDocument)
Set objPrjDoc = Nothing
建議使用方法 3,雖較繁瑣,但只要 DLL 與文件同目錄,即可確保程式碼可攜性,不受絕對路徑限制。
完成上述步驟後,即使不設定 VBA 專案密碼,外人也難以窺探核心程式碼,達到保護與效能雙重效果。