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

MFC 圓形進度條實現:GDI+ 繪製扇形覆蓋 Picture 控件

     編輯:程式設計綜合問答

需求分析

基於 MFC 實現圓環狀進度條(類似圖示效果),標準 CProgressCtrl 僅支持矩形,需自繪。

核心方案:雙緩衝 + 定時器驅動

  1. 界面佈局:對話框放置 Picture Control (ID: IDC_PIC_PROGRESS),類型設為 Owner Draw
  2. 變量關聯:CStatic m_picProgress; (DDX_Control)
  3. 核心繪製:重繪消息 WM_PAINT 中使用 GDI+ 繪製背景圓環 + 進度扇形

關鍵代碼片段

void CMyDlg::OnPaint() {
    CPaintDC dc(this);
    CRect rect;
    m_picProgress.GetClientRect(&rect);
    m_picProgress.ClientToScreen(&rect);
    ScreenToClient(&rect);

    Graphics g(dc.m_hDC);
    g.SetSmoothingMode(SmoothingModeAntiAlias);

    Pen penBg(Color(200,200,200), 10);      // 背景圓環
    Pen penFg(Color(0,180,0), 10);          // 進度顏色
    penFg.SetStartCap(LineCapRoundAnchor);
    penFg.SetEndCap(LineCapRoundAnchor);

    RectF bounds(rect.left, rect.top, rect.Width(), rect.Height());
    g.DrawEllipse(&penBg, bounds);          // 畫背景圓

    float sweepAngle = progress * 3.6f;     // 0-100 -> 0-360°
    g.DrawArc(&penFg, bounds, -90, sweepAngle); // 畫進度弧 (-90° 從頂部開始)
}

void CMyDlg::OnTimer(UINT_PTR nIDEvent) {
    if (nIDEvent == TIMER_PROGRESS) {
        if (progress >= 100) KillTimer(TIMER_PROGRESS);
        else { progress += 2; m_picProgress.Invalidate(); } // 觸發重繪
    }
    CDialogEx::OnTimer(nIDEvent);
}

關鍵優化點

  • 僅重繪 Picture 控件區域:m_picProgress.Invalidate() 避免整個對話框閃爍
  • 雙緩衝:GDI+ Graphics 內部雙緩衝,無需手動兼容 DC
  • 角度映射:進度 0-100 線性映射 -90° 到 270°,符合直觀順時針

繼承 CProgressCtrl 重繪同樣可行,但 Picture Control + GDI+ 更靈活,易實現漸變、圓角、動畫等高級效果。

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