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

C++Builder 實作任務列動畫圖示完整指南

     編輯:關於C++

引言:讓系統托盤圖示動起來

在 Windows 系統右下角通知區域(System Tray)顯示動畫圖示,能直觀反映應用程式狀態(如網路傳輸、備份進度、郵件接收)。本文示範如何在 C++Builder 中利用 TTimer 與 Shell_NotifyIcon API 實作幀動畫效果,以「門開關」動畫為例。

核心架構:通知圖示 API

Windows 透過 Shell_NotifyIcon 管理托盤圖示,支援三種操作:

  • NIM_ADD:新增圖示
  • NIM_MODIFY:更新圖示(動畫關鍵)
  • NIM_DELETE:移除圖示

函數原型:

WINSHELLAPI BOOL WINAPI Shell_NotifyIcon(
    DWORD dwMessage,           // NIM_ADD / NIM_MODIFY / NIM_DELETE
    PNOTIFYICONDATA lpData     // 圖示資料結構
);

關鍵資料結構:NOTIFYICONDATA

定義圖示行為與外觀的核心結構體:

typedef struct _NOTIFYICONDATA {
    DWORD cbSize;           // 結構大小
    HWND  hWnd;             // 接收回呼訊息的視窗
    UINT  uID;              // 圖示識別碼
    UINT  uFlags;           // 有效欄位旗標 (NIF_MESSAGE|NIF_ICON|NIF_TIP)
    UINT  uCallbackMessage; // 自訂回呼訊息 (如 WM_USER+1)
    HICON hIcon;            // 圖示控制代碼
    TCHAR szTip[128];       // 滑鼠懸停提示文字
    // ... 後續版本擴充欄位
} NOTIFYICONDATA, *PNOTIFYICONDATA;

完整實作步驟

1. 表單設計

  • 放置 TTimer (Timer1),設定 Interval = 1000 (1 秒/幀)
  • 放置兩個 TImage (Image1, Image2),分別載入「開門」、「關門」圖示 (.ico 格式)
  • 宣告全域變數 int n = 1; 控制幀切換

2. 發送通知訊息封裝

bool __fastcall TForm1::TrayMessage(DWORD dwMessage) {
    NOTIFYICONDATA tnd = {0};
    tnd.cbSize = sizeof(NOTIFYICONDATA);
    tnd.uCallbackMessage = MYWM_NOTIFY; // 自訂訊息常數
    tnd.hWnd = Handle;
    tnd.uID = IDC_MYICON;
    tnd.uFlags = NIF_MESSAGE | NIF_ICON | NIF_TIP;

    if (dwMessage == NIM_MODIFY) {
        tnd.hIcon = IconHandle(); // 取得當前幀圖示
        PSTR pszTip = TipText();  // 取得提示文字
        if (pszTip) 
            lstrcpyn(tnd.szTip, pszTip, sizeof(tnd.szTip));
        else 
            tnd.szTip[0] = '\0';
    } else {
        tnd.hIcon = NULL;
        tnd.szTip[0] = '\0';
    }
    return Shell_NotifyIcon(dwMessage, &tnd);
}

3. 圖示控制代碼取得

HICON __fastcall TForm1::IconHandle(void) {
    if (n == 1) 
        return Image1->Picture->Icon->Handle;
    else 
        return Image2->Picture->Icon->Handle;
}

4. 幀切換邏輯


void __fastcall TForm1::ToggleState(void) {
    n = (n == 1) ? 0 : 1; // 在 0、1 間切換
    TrayMessage(NIM_MODIFY); // 通知系統更新圖示
}

void __fastcall TForm1::Timer1Timer(TObject *Sender) {
    ToggleState(); // 每秒觸發一次幀切換
}

5. 初始化與清理


void __fastcall TForm1::FormCreate(TObject *Sender) {
    TrayMessage(NIM_ADD); // 程式啟動時加入托盤
    Timer1->Enabled = true;
}

void __fastcall TForm1::FormDestroy(TObject *Sender) {
    Timer1->Enabled = false;
    TrayMessage(NIM_DELETE); // 程式結束時移除
}

進階技巧與注意事項

動畫流暢度控制

  • 幀率:Interval 設定 100-200ms 可獲得較流暢動畫,但會增加 CPU 佔用。
  • 圖示尺寸:建議使用 16x16、32x32 多解析度圖示資源,適應不同 DPI 設定。

資源管理最佳實務

  • 圖示控制代碼 (HICON) 需配對 DestroyIcon 釋放,但 TImage::Picture::Icon::Handle 由 VCL 管理,手動釋放會導致重複釋放錯誤。
  • 程式異常終止時,托盤圖示可能殘留,建議在專案選項啟用「Application->HandleException」統一處理。

互動功能擴充

處理自訂回呼訊息 (MYWM_NOTIFY) 可實作:

  • 左鍵點擊:顯示/隱藏主視窗
  • 右鍵點擊:彈出功能選單 (還原、設定、離開)
  • 滑鼠懸停:動態更新提示文字顯示即時狀態

void __fastcall TForm1::WmNotifyIcon(TMessage &Msg) {
    switch (Msg.LParam) {
        case WM_LBUTTONDOWN:
            Visible = !Visible; // 切換視窗顯示
            break;
        case WM_RBUTTONDOWN:
            PopupMenu1->Popup(Mouse->CursorPos.X, Mouse->CursorPos.Y);
            break;
    }
}

完整程式碼架構

將上述邏輯整合後,專案結構如下:

  • Unit1.h:類別宣告、訊息映射、變數定義
  • Unit1.cpp:FormCreate、FormDestroy、Timer1Timer、TrayMessage、IconHandle、ToggleState、WmNotifyIcon 實作
  • 資源檔:door_open.ico、door_close.ico

結語

透過 Shell_NotifyIcon 配合定時器輪詢更新圖示,即可在 C++Builder 中輕鬆實作托盤動畫。此技術廣泛應用於即時通訊軟體、系統監控工具、備份程式等需長駐後台並提供視覺回饋的應用。開發者可根據需求擴充幀數、加入互動選單、整合應用程式狀態機,打造專業級使用者體驗。

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