void CVisualManager::OnUpdateCaptionButtons (CRect rectCaption, const CObList& lstSysButtons, CWnd* /*pWnd*/) { if (!CanDrawImage ()) { return; } CSize szSysBorder (GetSystemBorders ()); int nIndex = 3; int x = rectCaption.right + szSysBorder.cx - (szSysBorder.cx - 1); rectCaption.top -= szSysBorder.cy; for (POSITION pos = lstSysButtons.GetHeadPosition (); pos != NULL;) { CSize sizeButton (m_SysBtnBack[nIndex--].GetImageSize ()); x -= sizeButton.cx; CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*) lstSysButtons.GetNext (pos); ASSERT_VALID (pButton); pButton->SetRect (CRect (CPoint (x, rectCaption.top), sizeButton)); } return; }
//************************************************************************************* void CBCGPDlgImpl::OnTrackCaptionButtons (CPoint point) { if (CBCGPPopupMenu::GetActiveMenu () != NULL) { return; } UINT nHot = m_nHotSysButton; CBCGPFrameCaptionButton* pBtn = GetSysButton (OnNcHitTest (point)); if (pBtn != NULL && pBtn->m_bEnabled) { m_nHotSysButton = pBtn->GetHit (); pBtn->m_bFocused = TRUE; } else { m_nHotSysButton = HTNOWHERE; } if (m_nHotSysButton != nHot) { RedrawCaptionButton (pBtn); CBCGPFrameCaptionButton* pBtnOld = GetSysButton (nHot); if (pBtnOld != NULL) { pBtnOld->m_bFocused = FALSE; RedrawCaptionButton (pBtnOld); } } if (m_nHitSysButton == HTNOWHERE) { if (nHot != HTNOWHERE && m_nHotSysButton == HTNOWHERE) { ::ReleaseCapture(); } else if (nHot == HTNOWHERE && m_nHotSysButton != HTNOWHERE) { m_Dlg.SetCapture (); } } }
//************************************************************************* void CBCGPDlgImpl::UpdateCaptionButtons() { if ((m_Dlg.GetStyle () & WS_SYSMENU) == 0) { return; } CMenu* pSysMenu = m_Dlg.GetSystemMenu (FALSE); if (pSysMenu == NULL || !::IsMenu (pSysMenu->m_hMenu)) { return; } for (POSITION pos = m_lstCaptionSysButtons.GetHeadPosition (); pos != NULL;) { CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*)m_lstCaptionSysButtons.GetNext (pos); ASSERT_VALID (pButton); if (pButton->GetHit () == HTCLOSE_BCG) { BOOL bGrayed = pSysMenu->GetMenuState (SC_CLOSE, MF_BYCOMMAND) & MF_GRAYED; pButton->m_bEnabled = bGrayed ? FALSE : TRUE; } if (pButton->GetHit () == HTMAXBUTTON_BCG) { BOOL bGrayed = pSysMenu->GetMenuState (SC_MAXIMIZE, MF_BYCOMMAND) & MF_GRAYED; pButton->m_bEnabled = bGrayed ? FALSE : TRUE; } if (pButton->GetHit () == HTMINBUTTON_BCG) { BOOL bGrayed = pSysMenu->GetMenuState (SC_MINIMIZE, MF_BYCOMMAND) & MF_GRAYED; pButton->m_bEnabled = bGrayed ? FALSE : TRUE; } } #ifndef _BCGSUITE_ m_Dlg.SendMessage (BCGM_ONAFTERUPDATECAPTION); #endif m_Dlg.RedrawWindow (NULL, NULL, RDW_FRAME | RDW_INVALIDATE | RDW_UPDATENOW | RDW_NOCHILDREN); }
void CVisualManager::DrawNcCaption (CDC* pDC, CRect rectCaption, DWORD dwStyle, DWORD dwStyleEx, const CString& strTitle, const CString& strDocument, HICON hIcon, BOOL bPrefix, BOOL bActive, BOOL bTextCenter, const CObList& lstSysButtons) { const BOOL bIsRTL = (dwStyleEx & WS_EX_LAYOUTRTL) == WS_EX_LAYOUTRTL; const int nSysCaptionHeight = ::GetSystemMetrics (SM_CYCAPTION); CSize szSysBorder (GetSystemBorders ()); CDC memDC; memDC.CreateCompatibleDC (pDC); CBitmap memBmp; memBmp.CreateCompatibleBitmap (pDC, rectCaption.Width (), rectCaption.Height ()); CBitmap* pBmpOld = memDC.SelectObject (&memBmp); memDC.BitBlt (0, 0, rectCaption.Width (), rectCaption.Height (), pDC, 0, 0, SRCCOPY); BOOL bMaximized = (dwStyle & WS_MAXIMIZE) == WS_MAXIMIZE; CRect rectBorderCaption (rectCaption); if (bMaximized) { rectBorderCaption.OffsetRect (-rectBorderCaption.TopLeft ()); rectBorderCaption.bottom -= szSysBorder.cy; } m_ctrlMainBorderCaption.Draw (&memDC, rectBorderCaption, 0); CRect rectSysBtn (rectCaption); if (bMaximized) { rectSysBtn.top = 0; rectSysBtn.OffsetRect (szSysBorder.cx, 0); } rectSysBtn.right -= (szSysBorder.cx - 3); rectSysBtn.left = rectSysBtn.right - m_SysBtnBack[0].GetImageSize ().cx; m_SysBtnBack[0].DrawEx (&memDC, rectSysBtn, 0, CBCGPToolBarImages::ImageAlignHorzLeft, CBCGPToolBarImages::ImageAlignVertTop); CRect rectCaptionB (rectCaption); rectCaptionB.DeflateRect ((bMaximized ? 0 : szSysBorder.cx) - 1, 0); rectCaptionB.top = rectCaptionB.bottom - m_ctrlMainBorderCaptionB.GetParams ().m_rectImage.Height (); m_ctrlMainBorderCaptionB.Draw (&memDC, rectCaptionB, 0); CRect rect (rectCaption); rect.DeflateRect (szSysBorder.cx, szSysBorder.cy, szSysBorder.cx, 0); rect.top = rect.bottom - nSysCaptionHeight - 1; // Draw icon: if (hIcon != NULL) { CSize szIcon (::GetSystemMetrics (SM_CXSMICON), ::GetSystemMetrics (SM_CYSMICON)); long x = rect.left + (bMaximized ? szSysBorder.cx : 0) + 2; long y = rect.top + max (0, (nSysCaptionHeight - szIcon.cy) / 2); ::DrawIconEx (memDC.GetSafeHdc (), x, y, hIcon, szIcon.cx, szIcon.cy, 0, NULL, DI_NORMAL); rect.left = x + szIcon.cx + (bMaximized ? szSysBorder.cx : 4); } // Draw system buttons: int xButtonsRight = rect.right; for (POSITION pos = lstSysButtons.GetHeadPosition (); pos != NULL;) { CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*) lstSysButtons.GetNext (pos); ASSERT_VALID (pButton); BCGBUTTON_STATE state = ButtonsIsRegular; if (pButton->m_bPushed && pButton->m_bFocused) { state = ButtonsIsPressed; } else if (pButton->m_bFocused) { state = ButtonsIsHighlighted; } UINT uiHit = pButton->GetHit (); UINT nButton = 0; switch (uiHit) { case HTCLOSE_BCG: nButton = SC_CLOSE; break; case HTMAXBUTTON_BCG: nButton = (dwStyle & WS_MAXIMIZE) == WS_MAXIMIZE ? SC_RESTORE : SC_MAXIMIZE; break; case HTMINBUTTON_BCG: nButton = (dwStyle & WS_MINIMIZE) == WS_MINIMIZE ? SC_RESTORE : SC_MINIMIZE; break; } CRect rectBtn (pButton->GetRect ()); if (bMaximized) { rectBtn.OffsetRect (szSysBorder.cx, szSysBorder.cy); } DrawNcBtn (&memDC, rectBtn, nButton, state, FALSE, bActive, FALSE); xButtonsRight = min (xButtonsRight, pButton->GetRect ().left); } // Draw text: if ((!strTitle.IsEmpty () || !strDocument.IsEmpty ()) && rect.left < rect.right) { CFont* pOldFont = (CFont*)memDC.SelectObject (&m_AppCaptionFont); CRect rectText = rect; rectText.right = xButtonsRight - 1; DrawNcText (&memDC, rectText, strTitle, strDocument, bPrefix, bActive, bIsRTL, bTextCenter); memDC.SelectObject (pOldFont); } pDC->BitBlt (rectCaption.left, rectCaption.top, rectCaption.Width (), rectCaption.Height (), &memDC, 0, 0, SRCCOPY); memDC.SelectObject (pBmpOld); }
//***************************************************************************** void CMacStyle::DrawNcCaption (CDC* pDC, CRect rectCaption, DWORD dwStyle, DWORD dwStyleEx, const CString& strTitle, HICON hIcon, BOOL bActive, BOOL bTextCenter, const CObList& lstSysButtons) { const BOOL bIsRTL = (dwStyleEx & WS_EX_LAYOUTRTL) == WS_EX_LAYOUTRTL; const int nSysCaptionHeight = ::GetSystemMetrics (SM_CYCAPTION); CSize szSysBorder (GetSystemBorders ()); CDC memDC; memDC.CreateCompatibleDC (pDC); CBitmap memBmp; memBmp.CreateCompatibleBitmap (pDC, rectCaption.Width (), rectCaption.Height ()); memDC.SelectObject (&memBmp); memDC.BitBlt (0, 0, rectCaption.Width (), rectCaption.Height (), pDC, 0, 0, SRCCOPY); m_ctrlMainBorderCaption.Draw (&memDC, rectCaption, bActive ? 0 : 1); CRect rect (rectCaption); rect.DeflateRect (szSysBorder.cx, 0, szSysBorder.cx, 0); // Draw icon: if (hIcon != NULL) { CSize szIcon (::GetSystemMetrics (SM_CXSMICON), ::GetSystemMetrics (SM_CYSMICON)); CRect rectIcon (rect.TopLeft (), CSize (nSysCaptionHeight, rect.Height ())); long x = rect.left + max (0, (rectIcon.Width () - szIcon.cx) / 2); long y = rect.top + max (0, (rectIcon.Height () - szIcon.cy) / 2); ::DrawIconEx (memDC.GetSafeHdc (), x, y, hIcon, szIcon.cx, szIcon.cy, 0, NULL, DI_NORMAL); rect.left += rectIcon.Width (); } // Draw system buttons: int xButtonsRight = rect.right; for (POSITION pos = lstSysButtons.GetHeadPosition (); pos != NULL;) { CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*) lstSysButtons.GetNext (pos); ASSERT_VALID (pButton); BCGBUTTON_STATE state = ButtonsIsRegular; if (pButton->m_bPushed && pButton->m_bFocused) { state = ButtonsIsPressed; } else if (pButton->m_bFocused) { state = ButtonsIsHighlighted; } UINT uiHit = pButton->GetHit (); UINT nButton = 0; switch (uiHit) { case HTCLOSE_BCG: nButton = SC_CLOSE; break; case HTMAXBUTTON_BCG: nButton = (dwStyle & WS_MAXIMIZE) == WS_MAXIMIZE ? SC_RESTORE : SC_MAXIMIZE; break; case HTMINBUTTON_BCG: nButton = (dwStyle & WS_MINIMIZE) == WS_MINIMIZE ? SC_RESTORE : SC_MINIMIZE; break; } DrawNcBtn (&memDC, pButton->GetRect (), nButton, state, bActive); xButtonsRight = min (xButtonsRight, pButton->GetRect ().left); } // Draw text: if (!strTitle.IsEmpty () && rect.left < rect.right) { CFont* pOldFont = (CFont*)memDC.SelectObject (&m_AppCaptionFont); CRect rectText = rect; rectText.right = xButtonsRight - 1; DrawNcText (&memDC, rectText, strTitle, bActive, bIsRTL, bTextCenter); memDC.SelectObject (pOldFont); } pDC->BitBlt (rectCaption.left, rectCaption.top, rectCaption.Width (), rectCaption.Height (), &memDC, 0, 0, SRCCOPY); }
//************************************************************************* UINT CBCGPDlgImpl::OnNcHitTest (CPoint point) { m_Dlg.ScreenToClient (&point); if (!m_rectResizeBox.IsRectEmpty ()) { if (m_rectResizeBox.PtInRect(point)) { BOOL bRTL = m_Dlg.GetExStyle() & WS_EX_LAYOUTRTL; return bRTL ? HTBOTTOMLEFT : HTBOTTOMRIGHT; } } if (!IsOwnerDrawCaption ()) { return HTNOWHERE; } const CSize szSystemBorder(::GetSystemMetrics (SM_CXSIZEFRAME), ::GetSystemMetrics (SM_CYSIZEFRAME)); int cxOffset = szSystemBorder.cx; int cyOffset = szSystemBorder.cy; if (!m_Dlg.IsIconic ()) { cyOffset += GetCaptionHeight (); } if (m_Dlg.IsZoomed ()) { cxOffset -= szSystemBorder.cx; cyOffset -= szSystemBorder.cy; } point.Offset (cxOffset, cyOffset); for (POSITION pos = m_lstCaptionSysButtons.GetHeadPosition (); pos != NULL;) { CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*) m_lstCaptionSysButtons.GetNext (pos); ASSERT_VALID (pButton); if (pButton->GetRect ().PtInRect (point)) { return pButton->m_nHit; } } CRect rectCaption = GetCaptionRect (); if (rectCaption.PtInRect (point)) { if ((m_Dlg.GetExStyle () & WS_EX_TOOLWINDOW) == 0) { CRect rectSysMenu = rectCaption; rectSysMenu.right = rectSysMenu.left + ::GetSystemMetrics (SM_CXSMICON) + 2 + (m_Dlg.IsZoomed () ? szSystemBorder.cx : 0); return rectSysMenu.PtInRect (point) ? HTSYSMENU : HTCAPTION; } return HTCAPTION; } return HTNOWHERE; }
//************************************************************************* void CBCGPDlgImpl::UpdateCaption () { if (!IsOwnerDrawCaption ()) { return; } if (m_lstCaptionSysButtons.IsEmpty ()) { //------------------------ // Create caption buttons: //------------------------ const DWORD dwStyle = m_Dlg.GetStyle (); HMENU hSysMenu = NULL; CMenu* pSysMenu = m_Dlg.GetSystemMenu (FALSE); if (pSysMenu != NULL && ::IsMenu (pSysMenu->m_hMenu)) { hSysMenu = pSysMenu->GetSafeHmenu (); if (!::IsMenu (hSysMenu) || (m_Dlg.GetStyle () & WS_SYSMENU) == 0) { hSysMenu = NULL; } } if (hSysMenu != NULL) { m_lstCaptionSysButtons.AddTail (new CBCGPFrameCaptionButton (HTCLOSE_BCG)); if ((dwStyle & WS_MAXIMIZEBOX) == WS_MAXIMIZEBOX) { m_lstCaptionSysButtons.AddTail (new CBCGPFrameCaptionButton (HTMAXBUTTON_BCG)); } if ((dwStyle & WS_MINIMIZEBOX) == WS_MINIMIZEBOX) { m_lstCaptionSysButtons.AddTail (new CBCGPFrameCaptionButton (HTMINBUTTON_BCG)); } #ifndef _BCGSUITE_ if ((dwStyle & DS_CONTEXTHELP) == DS_CONTEXTHELP) { if (!m_Dlg.IsKindOf (RUNTIME_CLASS (CPropertySheet))) { m_lstCaptionSysButtons.AddTail (new CBCGPFrameCaptionButton (HTHELPBUTTON_BCG)); } } #endif } } CRect rectCaption = GetCaptionRect (); #ifndef _BCGSUITE_ if (!visualManagerMFC->OnUpdateNcButtons(&m_Dlg, m_lstCaptionSysButtons, rectCaption)) #endif { CSize sizeButton = visualManagerMFC->GetNcBtnSize (FALSE); sizeButton.cy = min (sizeButton.cy, rectCaption.Height () - 2); int x = rectCaption.right - sizeButton.cx; int y = rectCaption.top + max (0, (rectCaption.Height () - sizeButton.cy) / 2); for (POSITION pos = m_lstCaptionSysButtons.GetHeadPosition (); pos != NULL;) { CBCGPFrameCaptionButton* pButton = (CBCGPFrameCaptionButton*) m_lstCaptionSysButtons.GetNext (pos); ASSERT_VALID (pButton); pButton->SetRect (CRect (CPoint (x, y), sizeButton)); x -= sizeButton.cx; } } #ifndef _BCGSUITE_ m_Dlg.SendMessage (BCGM_ONAFTERUPDATECAPTION); #endif m_Dlg.RedrawWindow (NULL, NULL, RDW_FRAME | RDW_INVALIDATE | RDW_UPDATENOW | RDW_NOCHILDREN); }