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

Delphi 元件開發實戰入門:從 TCustomPanel 繼承打造倒數計時器元件

     編輯:Delphi

元件開發是 Delphi 進階的分水嶺。本文以倒數計時器元件 TTimeCount 為完整案例,演示從繼承層級選擇、成員/屬性/方法/事件設計、祖先屬性顯化、封裝安裝與圖示製作 的標準化流程。所有程式碼經 Delphi 7 驗證。

一、確定繼承層級:為何選 TCustomPanel?

  • 需求:可視化容器、顯示數字、可設定邊框/顏色/字型
  • TPanel 只是將 TCustomPanel 的 protected 屬性在 published 區重新宣告(顯化)
  • 我們不需要所有 Panel 屬性,直接繼承 TCustomPanel 並按需顯化,更乾淨

二、核心成員設計

type
  TInterval = (TenM, TwentyM, ThirtyM, FortyM, FiftyM, SixtyM); // 觸發間隔列舉

  TTimeCount = class(TCustomPanel)
  private
    FTimer: TTimer;           // 核心計時器
    FCount: Integer;          // 秒數計數器(0-3599 循環)
    FInterval: TInterval;     // 觸發間隔設定
    FActive: Boolean;         // 是否啟用間隔事件
    TimeLen: Integer;         // 間隔對應秒數(內部用)
    TimeNum: Integer;         // 已計秒數(內部用)
    FTimeOut: TNotifyEvent;   // 間隔事件代理
    procedure SetInterval(I: TInterval);
    procedure SetActive(A: Boolean);
    procedure FTimerTimer(Sender: TObject); // TTimer.OnTimer 處理
  protected
    procedure DoTimeOut; dynamic; // 事件調度器
  public
    constructor Create(AOwner: TComponent); override;
    destructor Destroy; override;
    procedure Start;   // 從 0 開始
    procedure Stop;    // 歸零停止
    procedure Pause;   // 暫停
    procedure Resume;  // 繼續
    property Count: Integer read FCount; // 唯讀屬性,僅運行期取值
  published
    property Interval: TInterval read FInterval write SetInterval default TenM;
    property Active: Boolean read FActive write SetActive default False;
    property OnTimeOut: TNotifyEvent read FTimeOut write FTimeOut;
    // 按需顯化祖先屬性
    property BevelInner; property BevelOuter; property BevelWidth;
    property Color; property Font; property PopupMenu; property ShowHint;
    property TabOrder; property TabStop; property Visible;
    property OnClick; property OnDblClick; property OnMouseDown;
    property OnMouseMove; property OnMouseUp;
  end;

三、建構子/解構子與 TTimer 初始化


constructor TTimeCount.Create(AOwner: TComponent);
  procedure CreateTimer;
  begin
    FTimer := TTimer.Create(Self);
    FTimer.Enabled := False;
    FTimer.Interval := 1000; // 1 秒
    FTimer.OnTimer := FTimerTimer;
  end;
  procedure SetView; // 預設外觀
  begin
    Width := 100; Height := 50;
    Color := clBlack; Font.Color := clWhite; Font.Size := 14;
    Font.Style := [fsBold, fsUnderline];
    BevelOuter := bvLowered; Caption := '0';
  end;
begin
  inherited Create(AOwner);
  FCount := 0; FInterval := TenM; FActive := False;
  TimeLen := 600; TimeNum := 0; // 預設 10 分鐘
  CreateTimer; SetView;
end;

destructor TTimeCount.Destroy;
begin
  FTimer.Free;
  inherited Destroy;
end;

四、核心邏輯:FTimerTimer 與 DoTimeOut


procedure TTimeCount.FTimerTimer(Sender: TObject);
begin
  Inc(FCount);
  if (FCount mod 3600) = 0 then FCount := 0; // 1 小時歸零
  Caption := IntToStr(FCount); // 直接顯示於 Panel Caption

  Inc(TimeNum);
  if (TimeNum = TimeLen) and FActive then begin
    DoTimeOut; // 觸發間隔事件
    TimeNum := 0;
  end;
end;

procedure TTimeCount.DoTimeOut;
begin
  if Assigned(FTimeOut) then FTimeOut(Self);
end;

五、公開方法實作


procedure TTimeCount.Start;
begin
  if (not FTimer.Enabled) and (TimeNum = 0) then FTimer.Enabled := True;
end;

procedure TTimeCount.Stop;
begin
  FTimer.Enabled := False; FCount := 0; TimeNum := 0; Caption := '0';
end;

procedure TTimeCount.Pause;
begin
  if FTimer.Enabled then FTimer.Enabled := False;
end;

procedure TTimeCount.Resume;
begin
  if not FTimer.Enabled then FTimer.Enabled := True;
end;

procedure TTimeCount.SetInterval(I: TInterval);
begin
  if FInterval <> I then begin
    FInterval := I;
    case FInterval of
      TenM: TimeLen := 600; TwentyM: TimeLen := 1200; ThirtyM: TimeLen := 1800;
      FortyM: TimeLen := 2400; FiftyM: TimeLen := 3000; SixtyM: TimeLen := 3600;
    end;
  end;
end;

procedure TTimeCount.SetActive(A: Boolean);
begin
  if FActive <> A then begin
    FActive := A; TimeNum := 0;
  end;
end;

六、元件封裝、安裝與圖示製作

  1. 將單元存為 TimeCount.pas,放入專用資料夾(如 $(DELPHI)\MyCom\)
  2. IDE 選單 Component → New Component:
    • Ancestor Type: TCustomPanel
    • Class Name: TTimeCount
    • Palette Page: Samples(或自訂)
    • Unit File Name: TimeCount
    • Search Path: 加入 MyCom 路徑
  3. 產生樣板碼後,用完整類別程式碼替換(保留 Register 程序)
  4. Component → Install Component,Unit file name 指向 TimeCount.pas,Package 選 dclusr.dpk,確定編譯安裝
  5. 製作圖示: 開啟 Image Editor → 新建 .dcr → 建立 24×24 位圖 → 名稱 TTIMECOUNT(大寫類別名) → 存檔為 TIMECOUNT.dcr 放入單元目錄 → 重新安裝
  6. 若需移除:File → Open → dclusr.dpk → Contains 選中 TimeCount.pas → Remove → Compile

七、測試使用


procedure TForm1.FormCreate(Sender: TObject);
begin
  TimeCount1.Interval := ThirtyM; // 30 分鐘觸發
  TimeCount1.Active := True;
  TimeCount1.OnTimeOut := TimeCount1TimeOut;
  TimeCount1.Start;
end;

procedure TForm1.TimeCount1TimeOut(Sender: TObject);
begin
  Beep; // 或 ShowMessage('休息時間到!');
end;

此元件結構清晰、邏輯自洽,是學習 VCL 元件開發流程的最佳範本。掌握此流程,即可著手開發更複雜的資料感知、圖形繪製、複合型元件。

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