前幾天在設計一個以 ActiveX Control 為主的小系統,使用該死的 VB 語言。
之所以選用這種 Web Control 的原因是避免 deployment 時的麻煩,因為這是一個大機關要使用的軟體,如果要一一進行軟體部署配置,恐怕非常吃力不討好,此外,每次軟體升級時,又來再來一次,想來實在恐
拉好介面,寫好物件類別後,用 PDW 把檔案包裝成 cab 檔案,並產生 INF 安裝檔與 HTML 檔案。我修改了 HTML 檔案,加入一些啟動時需要的參數,以 <param> 傳 Object Parameter 進去。但是執行的時候卻出現:
「這個畫面上某個 ActiveX 控制項與其他部分相作用時可能會不安全,要允許相互作用?」
這個問題非常有趣,允許就空空也,不允許卻也正常運作,但是如此一來便不能正確指定相關的預設參數給程式。 🙁 一點都弄不清楚到底哪個環節出了問題。
後來我知道那是 PDW 的 bug。微軟知識庫 221541 提到,可以手動加登錄資訊到 INF 檔案中,可以修好將元件設計為可安全初始化與指令碼處理。比較好的作法其實是 182598 在 Visual Basic 控制項中實作 IObjectSafety 介面,所以最後我還是實作了 IObjectSafety。學著用 MkTypLib.exe 編譯 ODL 檔案成為 TLB。然後補上一些漏掉的程式碼。
理論上所謂的控制項安全根本就是讓開發者自行憑著良心選擇的。這個安全機制一點都不安全。
然而奇怪的問題還是存在,我必須使用 <param> 來指定初始化的值,但是只要我一加進 <param> 這個標籤,開了 IE 後,就畫面空白一片,甚麼也看不到。拿掉後就可以正常運作。
知識庫 169438 說到幾個可能的原因
- 缺少 ActiveX 控制項使用的相關 DLL
- 使用授權 ActiveX 控制項時缺少 .lpk 檔案。
- ActiveX 控制項包含其它需要執行階段授權合約的控制項。
- ActiveX 控制項的 <OBJECT> 標幟中缺少 CODEBASE 屬性
雖然應該不是上述的問題,但是我還是盡可能把引用的元件拿掉,用 Lpk_Tool.Exe 建立授權合約也就是 LPK 檔案,還抓了 Internet Component Download Online Troubleshooter 來除錯,卻一點問題也沒有。
直到最後,終於了解,原來是豬頭我自己犯的錯,建立 <object> 後,我用 <param> 指定數值後,那個 ActiveX Control 便會把所有的屬性重置,所以其實那個 ActiveX Control 早已正確的跑起來了。但是長度與寬度都是 0 ! 所以就等於隱形看不到了。補充指定 <object width=”..” height=..> 等即可正確使用此元件。
結論。Visual Basic 真是個令人厭的東西。
參考資料
- Safe Initialization and Scripting for ActiveX Controls
- 微軟知識庫文件 – 221541 FIX: Failed to Mark Safe for Scripting Using Visual Basic PDW http://support.microsoft.com/default.aspx?scid=kb;en-us;221541
- 微軟知識庫文件 – 182598 HOWTO:在 Visual Basic 控制項中實作 IObjectSafety http://support.microsoft.com/default.aspx?scid=kb;zh-tw;182598
- 微軟知識庫文件 – 165075 HOWTO:使用 .inf 檔在 Internet Explorer 中下載相依的 DLL http://support.microsoft.com/default.aspx?scid=kb;zh-tw;165075
- 微軟知識庫文件 – 169438 PRB: Web 網頁上無法正常顯示 ActiveX 控制項。 http://support.microsoft.com/default.aspx?scid=kb;zh-tw;169438
- 「型別程式庫編譯器」(MkTypLib.exe) http://support.microsoft.com/servicedesks/fileversion/dllinfo.asp
- Microsoft DLL Help database http://support.microsoft.com/servicedesks/fileversion/dllinfo.asp
- Code Download Log Viewer (CDLLOGVW)