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

C++Builder 元件開發深度指南:類別宣告、屬性/事件機制、封裝註冊全流程

     編輯:關於C++

開發可在 IDE 設計期操作的 VCL 元件,需遵循嚴格的類別結構、屬性/事件宣告模式與註冊流程。本文系統整理 PACKAGE 類別宣告、__property 讀寫存取器、__published 設計期可見性、事件型別定義與觸發、RegisterComponents 封裝安裝全細節,並給出標準範本程式碼。

一、標準類別宣告骨架

class PACKAGE TMyComponent : public TComponent { // 或 TGraphicControl, TCustomControl
private:
    // 1. 內部實作細節
    // 2. 屬性備份欄位 (F開頭)
    AnsiString FCaption;
    // 3. 事件備份欄位
    TNotifyEvent FOnClick;
    // 4. 祖先類型別名,便於呼叫 inherited
    typedef TComponent Inherited;

    // 私有方法:僅內部使用,盡量寫成通用工具函數
    void InternalUpdate();

protected:
    // 受保護虛擬方法:派生類可重寫並決定是否公開
    virtual void __fastcall Loaded(); // 元件載入完成
    virtual void __fastcall Paint();  // 繪圖 (TGraphicControl 以上)

    // 事件觸發器:命名慣例 Do + 事件名
    virtual void __fastcall DoClick(TObject* Sender) {
        if (FOnClick) FOnClick(Sender); // 安全觸發
    }

public:
    __fastcall TMyComponent(TComponent* Owner);
    __fastcall ~TMyComponent();

    // 公開方法:執行期 API
    void RefreshData();

__published:
    // 設計期可見屬性:物件檢視器可編輯、屬性編輯器支援
    __property AnsiString Caption = {
        read=FCaption, write=FCaption, default="MyComponent"
    };
    // 或使用存取器方法 (含副作用邏輯)
    __property AnsiString Text = {
        read=GetText, write=SetText, stored=true, default=""
    };

    // 設計期可見事件
    __property TNotifyEvent OnClick = { read=FOnClick, write=FOnClick };
};

二、屬性宣告完整語法

__property Type Name = {
    read = FieldOrMethod,   // 必填
    write = FieldOrMethod,  // 可省略 (唯讀)
    default = Value,        // 預設值,影響 DFM 儲存 (不存預設值)
    stored = True/False,    // 是否存入 DFM
    nodefault,              // 無預設值
    index = Integer,        // 共用存取器時的索引
    implements = Interface  // 介面委派 (進階)
};

存取器模式範例 (含副作用)

private:
    AnsiString FText;
    AnsiString __fastcall GetText() { return FText; }
    void __fastcall SetText(const AnsiString& Value) {
        if (FText != Value) {
            FText = Value;
            InternalUpdate(); // 副作用:重繪、重算、通知...
        }
    }
__published:
    __property AnsiString Text = { read=GetText, write=SetText };

三、事件機制:從型別定義到觸發

1. 簡單事件 (單參數 Sender)

__property TNotifyEvent OnChange = { read=FOnChange, write=FOnChange };
// TNotifyEvent = void __fastcall (__closure *)(TObject* Sender)

2. 複雜事件 (多參數、引用回傳)

// 1. 定義事件型別 (類似函數指標)
typedef void __fastcall (__closure *TKeyEvent)(TObject* Sender, WORD& Key, TShiftState Shift);

// 2. 私有備份欄位
TKeyEvent FOnKeyDown;

// 3. protected 觸發器 (虛擬,可被覆寫)
virtual void __fastcall DoKeyDown(TObject* Sender, WORD& Key, TShiftState Shift) {
    if (FOnKeyDown) FOnKeyDown(Sender, Key, Shift);
}

// 4. __published 發布
__property TKeyEvent OnKeyDown = { read=FOnKeyDown, write=FOnKeyDown };

3. 事件觸發時機

  • 鍵盤/滑鼠訊息處理函數中呼叫 DoKeyDown(...)
  • 屬性設定器中呼叫 DoChange(this)
  • 非同步作業完成 (Thread/Timer) 同步至主執行緒呼叫

四、元件檢查與註冊

// 靜態檢查:確保無純虛擬函數,可實例化
static inline void ValidCtrCheck(TMyComponent*) {
    new TMyComponent(NULL); // 僅編譯期檢查,不會真正執行
}

namespace Mycomponent { // 命名空間 = 檔名小寫 (慣例)
    void __fastcall PACKAGE Register() {
        TComponentClass classes[1] = { __classid(TMyComponent) };
        RegisterComponents("My Components", classes, 0); // 頁面名稱、類別陣列、索引
    }
}
  • PACKAGE 關鍵字確保編譯為設計期套件 (.bpl)
  • 命名空間必須與單元檔名對應 (如 MyComponent.cpp → namespace Mycomponent)
  • 使用 Component → New Component 精靈可自動生成上述樣板

五、建置與安裝流程

  1. 專案類型選 Package (File → New → Package)
  2. Contains 加入元件單元 (.cpp)
  3. Requires 加入 vcl, rtl, designide (設計期介面)
  4. 編譯產出 MyPackage.bpl + MyPackage.dcp
  5. Component → Install Packages → Add 選擇 .bpl 安裝至 IDE
  6. 元件面板指定頁面出現新元件圖示

六、進階主題

主題關鍵點
屬性編輯器繼承 TPropertyEditor,RegisterPropertyEditor 註冊,支援下拉、對話框、子屬性
元件編輯器繼承 TComponentEditor,右鍵選單加入動詞、雙擊預設動作
設計期繪圖覆寫 Paint,使用 Canvas 繪製非視窗控制項外觀
線上說明整合HelpKeyword, HelpContext 屬性關聯 CHM 主題
版本資訊GetPackageInfo 讀取 BPL 版本、描述、作者

七、最佳實踐清單

  • 建構子:初始化所有備份欄位、呼叫 inherited、設定預設尺寸/色彩
  • 解構子:釋放內建資源、取消事件訂閱
  • Loaded:設計期屬性全部載入後執行,適合依賴多屬性的初始化
  • SetParent:父視窗變更時更新字型/色彩繼承
  • ReadState/WriteState:自訂串流化邏輯 (罕見)
  • 定義 PACKAGE 宏於專案選項 Package 頁面自動處理

八、總結

C++Builder 元件開發核心在於:PACKAGE 類別、__property 存取器封裝副作用、事件型別+觸發器分離、__published 設計期可見性、RegisterComponents 封裝安裝。掌握此標準流程,即可將任何演算法、硬體介面、第三方庫包裝為可視化拖放元件,大幅提升團隊復用效率。

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