首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> VC >> VC 教學

VC++中使用ATL創建ActiveX控件完整教程

     編輯:VC 教學

ActiveX 控件技術概述

ActiveX 控件是微軟提供的強大元件開發技術,屬於 COM 元件技術的核心部分。作為 OLE 的第三個版本,它最大的擴展在於增加了 Internet 功能——不僅可在支援 OLE 的容器中使用,更能直接嵌入網頁成為網頁元件。ActiveX 控件作為可重用元件,相當於封裝良好的程式碼模組,透過方法、屬性、事件與應用程式通訊。其與開發語言無關的特性,使得任何支援 ActiveX 的平台皆可使用,實現了軟體生產的工業化,大幅降低開發成本、提高生產效率,達到資源共享。

ATL 技術介紹

什麼是 ATL?

ATL (Active Template Library) 是一套 C++ 模板庫。使用 ATL 能快速開發出高效、精簡的程式碼,同時對 COM 元件開發提供最大程度的程式碼自動生成與視覺化支援。自 Visual C++ 5.0 起,微軟將 ATL 整合進 VC++ 開發環境,現已成為標準開發工具的重要成員。

ATL 與傳統開發方式對比

開發方式優點缺點
COM SDK 直接開發最基礎、最靈活難度大、工作量大、需深入理解 COM、大量重複勞動
MFC COM 支援提高自動化程度、縮短開發時間、面向物件封裝程式碼冗余大、必須依賴 MFC 執行庫
ATL 技術高效精簡、自動生成程式碼、視覺化支援、無額外執行庫依賴學習曲線稍陡峭

ATL 核心技術包括:COM 技術、C++ 模板類技術、C++ 多重繼承技術。

ATL 基本開發流程

  1. 建立新的 ATL 專案,配置專案選項
  2. 向專案新增 ATL 類別,進行初始配置
  3. 根據需求加入介面定義,實作介面成員函式
  4. 編譯連結專案,註冊 COM 元件

實作範例:建立 CircleCtl ActiveX 控件

步驟 1:建立 ATL 專案

  • 使用 ATL COM AppWizard 建立專案,命名為 Circle
  • 按精靈預設設定,Server Type 選 Dynamic Link Library (DLL)

步驟 2:新增 ActiveX 控件

  1. 插入/新增 ATL 物件 → 開啟 ATL Object Wizard
  2. 左側 Category 選 Object,右側選 Full Control → Next
  3. Names 索引標籤:Short Name 輸入 CircleCtl,其餘自動生成
  4. Attributes 索引標籤:勾選 Support ISupportErrorInfo(錯誤資訊支援)與 Support Connection Points(連接點支援)
  5. Miscellaneous 保持預設
  6. Stock Properties:將 FillColor 加入支援清單
  7. 確定完成控件加入

步驟 3:實作控件繪製邏輯

在生成的 CircleCtl.cpp 中實作 OnDraw 方法:

HRESULT CircleCtl::OnDraw(ATL_DRAWINFO& di) {
    RECT& rc = *(RECT*)di.prcBounds;
    HDC hdc = di.hdcDraw;

    // 建立筆刷與畫筆
    HBRUSH hBrush = CreateSolidBrush(TranslateColor(m_clrFillColor));
    HPEN hPen = CreatePen(PS_SOLID, 1, RGB(0, 0, 0));
    HBRUSH hOldBrush = (HBRUSH)SelectObject(hdc, hBrush);
    HPEN hOldPen = (HPEN)SelectObject(hdc, hPen);

    // 繪製圓形
    int cx = (rc.left + rc.right) / 2;
    int cy = (rc.top + rc.bottom) / 2;
    int radius = min((rc.right - rc.left), (rc.bottom - rc.top)) / 2 - 2;
    Ellipse(hdc, cx - radius, cy - radius, cx + radius, cy + radius);

    // 恢復並清理
    SelectObject(hdc, hOldBrush);
    SelectObject(hdc, hOldPen);
    DeleteObject(hBrush);
    DeleteObject(hPen);
    return S_OK;
}

步驟 4:加入自訂屬性與方法

透過類別檢視,在 ICircleCtl 介面加入:

  • 屬性:Radius (long)、BorderColor (OLE_COLOR)
  • 方法:Reset()、Animate(BOOL enable)
  • 事件:Click()、DblClick()、RadiusChanged(long newRadius)

實作範例(屬性存取):

STDMETHODIMP CircleCtl::get_Radius(long* pVal) {
    *pVal = m_nRadius;
    return S_OK;
}

STDMETHODIMP CircleCtl::put_Radius(long newVal) {
    if (newVal < 0) return E_INVALIDARG;
    m_nRadius = newVal;
    Fire_RadiusChanged(newVal);  // 觸發事件
    InvalidateControl();         // 重繪
    return S_OK;
}

控件測試與部署

1. 使用 ActiveX Control Test Container 測試

  • 編譯專案後,工具列會出現 ActiveX Control Test Container
  • 選單 Edit/Insert New Control 選擇 CircleCtl 測試屬性、方法、事件

2. 網頁嵌入測試

<html>
<body>
<object id="circle1" classid="clsid:YOUR_CLSID_HERE" width="200" height="200">
    <param name="FillColor" value="#FF0000">
    <param name="Radius" value="50">
</object>
<script>
    circle1.Animate(true);
    circle1.Radius = 80;
</script>
</body>
</html>

3. 部署注意事項

  • 需將生成的 .ocx 檔案註冊到目標機器:regsvr32 CircleCtl.ocx
  • 確保目標機有對應版本的 VC++ 執行庫
  • 網頁使用需設定正確的 classid(可從註冊表或 .idl 檔獲取)
  • 考慮簽署 CAB 檔案以便 IE 自動下載安裝

進階主題

連接點與事件觸發

ATL 透過 IConnectionPointContainer 實作事件。定義事件介面 _ICircleCtlEvents,在 .idl 中宣告:

dispinterface _ICircleCtlEvents {
    properties:
    methods:
        void Click();
        void DblClick();
        void RadiusChanged([in] long newRadius);
};

觸發事件使用 ATL 產生的 Fire_* 方法,如 Fire_RadiusChanged(newVal)。

持久化儲存

實作 IPersistStreamInit、IPersistStorage、IPersistPropertyBag 介面,覆寫 Load/Save 方法,將屬性值序列化儲存。

常見問題排查

問題可能原因解決方案
控件不顯示OnDraw 未正確繪製、尺寸為 0檢查 OnDraw 邏輯、確保 InvalidateControl() 調用
屬性不保存未實作持久化介面加入 IPersist* 介面並實作 Load/Save
事件不觸發連接點未正確建立檢查 .idl 事件定義、確認 Fire_* 調用
網頁無法載入classid 錯誤、OCX 未註冊、安全性設定驗證 classid、執行 regsvr32、調整 IE 安全等級

結語

ATL 提供了高效、輕量的 ActiveX 控件開發框架。掌握專案建立、介面定義、繪製邏輯、屬性方法事件實作、持久化與部署流程,即可開發出專業級的可重用控件。結合網頁嵌入能力,ActiveX 控件仍是特定企業級應用的重要技術選擇。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved