www.gusucode.com > 自定义边框和圆角效果的VC++漂亮窗体源码程序 > 自定义边框和圆角效果的VC++漂亮窗体/RoundRect/RoundRect/BtnMenu.cpp
******************************************************************************** // BtnMenu.cpp : implementation file // Download by http://www.codesc.net #include "stdafx.h" #include "RoundRect.h" #include "BtnMenu.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // CBtnMenu CBtnMenu::CBtnMenu() { m_clrText = GetSysColor (COLOR_BTNTEXT); m_clrBack = GetSysColor (COLOR_BTNFACE); m_brBackground.CreateSolidBrush (m_clrBack); m_crText = m_clrText; m_bLBtnDown = FALSE; m_idCursor = 0; m_idBitmap = 0; } CBtnMenu::~CBtnMenu() { if ((HBRUSH) m_brBackground != NULL) m_brBackground.DeleteObject (); } BEGIN_MESSAGE_MAP(CBtnMenu, CButton) //{{AFX_MSG_MAP(CBtnMenu) ON_WM_CTLCOLOR_REFLECT() ON_WM_MOUSEMOVE() ON_WM_LBUTTONDOWN() ON_WM_LBUTTONUP() ON_WM_TIMER() //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CBtnMenu message handlers HBRUSH CBtnMenu::CtlColor(CDC* pDC, UINT nCtlColor) { // TODO: Change any attributes of the DC here // TODO: Return a non-NULL brush if the parent's handler should not be called return NULL; } void CBtnMenu::OnMouseMove(UINT nFlags, CPoint point) { //Here I will set a timer and see if the current cursor is within our boundaries if // not kill the timer and remove the current highlighting SetTimer (1,55,NULL); CButton::OnMouseMove(nFlags, point); } void CBtnMenu::OnLButtonDown(UINT nFlags, CPoint point) { // TODO: Add your message handler code here and/or call default m_bLBtnDown= TRUE; CButton::OnLButtonDown(nFlags, point); } void CBtnMenu::OnLButtonUp(UINT nFlags, CPoint point) { // TODO: Add your message handler code here and/or call default m_bLBtnDown= FALSE; //Take out the cursor CButton::OnLButtonUp(nFlags, point); } void CBtnMenu::DrawItem(LPDRAWITEMSTRUCT lpDIS) { ASSERT(lpDIS != NULL); CDC* pDC = CDC::FromHandle(lpDIS->hDC); CRect rect; HBITMAP hBitmap =NULL; // draw the colored rectangle portion rect.CopyRect(&lpDIS->rcItem); // draw the up/down/focused/disabled state UINT state = lpDIS->itemState; if ( (state & ODS_SELECTED) ) { // draw the down edges CBrush *pOldBrush = pDC->SelectObject(&m_brBackground); pDC->RoundRect(rect.left, rect.top, rect.Width(), rect.Height(), 2, 2); pDC->SelectObject(pOldBrush); if (m_idBitmap) hBitmap = (HBITMAP) LoadImage (AfxGetInstanceHandle (),MAKEINTRESOURCE (m_idBitmap), IMAGE_BITMAP,0,0,LR_DEFAULTCOLOR|LR_LOADMAP3DCOLORS|LR_LOADTRANSPARENT); pDC->Draw3dRect (rect,GetSysColor (COLOR_3DDKSHADOW),GetSysColor (COLOR_3DHILIGHT)); } else { CBrush *pOldBrush = pDC->SelectObject(&m_brBackground); pDC->RoundRect(rect.left, rect.top, rect.Width(), rect.Height(), 2, 2); pDC->SelectObject(pOldBrush); if (m_idBitmap) hBitmap = (HBITMAP) LoadImage (AfxGetInstanceHandle (),MAKEINTRESOURCE (m_idBitmap), IMAGE_BITMAP,0,0,LR_MONOCHROME|LR_LOADMAP3DCOLORS); // draw the up edges pDC->Draw3dRect (rect,m_clrBack,m_clrBack); } // draw the text if there is any //We have to paint the text only if the image is nonexistant CString strText; GetWindowText(strText); if ( !strText.IsEmpty()) { LOGFONT lf; ZeroMemory ((PVOID) &lf,sizeof (LOGFONT)); CFont * pFont = GetFont(); CFont dispFont; pFont->GetLogFont (&lf); if ((state & ODS_SELECTED)) { lf.lfWeight = FW_EXTRABOLD; dispFont.CreateFontIndirect (&lf); pFont = pDC->SelectObject (&dispFont); //While selected move the text a bit rect.top +=2; rect.left +=2; rect.right -=2; rect.bottom -=2; } int iOldMode = pDC->GetBkMode(); COLORREF crOldText = pDC->GetTextColor(); pDC->SetBkMode( TRANSPARENT ); pDC->SetTextColor( m_crText ); if (state & ODS_FOCUS ) { if (!(state & ODS_SELECTED)) { lf.lfUnderline = TRUE; lf.lfWeight = FW_LIGHT; dispFont.CreateFontIndirect (&lf); pFont = pDC->SelectObject (&dispFont); if (m_idBitmap) hBitmap =(HBITMAP) LoadImage (AfxGetInstanceHandle (),MAKEINTRESOURCE (m_idBitmap), IMAGE_BITMAP,0,0,LR_DEFAULTCOLOR|LR_LOADMAP3DCOLORS|LR_LOADTRANSPARENT); } } if (state & ODS_DISABLED) { CBrush grayBrush; grayBrush.CreateSolidBrush (GetSysColor (COLOR_GRAYTEXT)); pDC->GrayString (&grayBrush,NULL,(LPARAM)((LPCSTR)strText),-1,rect.left, rect.top,rect.Width(),rect.Height()); } else { if (!hBitmap) pDC->DrawText(strText, rect, DT_LEFT | DT_VCENTER |DT_CENTER| DT_SINGLELINE); else { CDC memdc; CBitmap bmp; CBitmap *poldbmp; bmp.Attach (hBitmap); BITMAP bitmap; bmp.GetBitmap (&bitmap); memdc.CreateCompatibleDC( pDC ); // Select the bitmap into the DC poldbmp = memdc.SelectObject( &bmp); // Copy (BitBlt) bitmap from memory DC to screen DC pDC -> StretchBlt( rect.left,rect.top, rect.right-rect.left, rect.bottom -rect.top, &memdc, 0,0, bitmap.bmWidth,bitmap.bmHeight,SRCCOPY ); memdc.SelectObject( poldbmp ); bmp.Detach (); } } pDC->SetBkMode( iOldMode ); pDC->SetTextColor( crOldText ); pDC->SelectObject (pFont); //set it to the old font dispFont.DeleteObject (); } if ( (state & ODS_DISABLED) ) { //AST - how should we indicate this??? } } void CBtnMenu::OnTimer(UINT nIDEvent) { POINT pt; static BOOL pPainted = FALSE; GetCursorPos(&pt); CRect rect; GetWindowRect (rect); if (m_bLBtnDown) { KillTimer (1); //Take the cursor out if the man has pressed de button if (m_idCursor) { ::SetCursor (AfxGetApp () -> LoadStandardCursor (IDC_ARROW)); } if (pPainted) InvalidateRect (NULL); pPainted = FALSE; return; } if (!rect.PtInRect (pt)) { KillTimer (1); //Take out the cursor if the thing is out if (m_idCursor) { ::SetCursor (AfxGetApp () -> LoadStandardCursor (IDC_ARROW)); } if (pPainted) InvalidateRect (NULL); pPainted = FALSE; return; } else { if (pPainted) return; else pPainted = TRUE; //Here we need to put the cursor in for the settings if (m_idCursor) { HCURSOR hCursor = AfxGetApp () -> LoadCursor (m_idCursor); ::SetCursor (hCursor); } CDC *pDC = GetDC (); if (!m_idBitmap) { LOGFONT lf; ZeroMemory ((PVOID) &lf,sizeof (LOGFONT)); CFont * pFont = GetFont(); CFont dispFont; pFont->GetLogFont (&lf); lf.lfUnderline = TRUE; lf.lfWeight = FW_BOLD; int iOldMode = pDC->GetBkMode(); COLORREF crOldText = pDC->GetTextColor(); dispFont.CreateFontIndirect (&lf); pDC->SetBkMode( TRANSPARENT ); pDC->SetTextColor( m_crText); pDC -> SelectObject (dispFont); CString strText; GetWindowText (strText); CRect rect; GetClientRect (rect); //pDC->FillSolidRect (rect,m_clrBack); pDC->FillSolidRect (rect,0x00ffffff);//置背景色 pDC->DrawFocusRect(&rect); pDC->DrawText(strText, rect, DT_LEFT | DT_VCENTER |DT_CENTER| DT_SINGLELINE); pDC->SetBkMode( iOldMode ); pDC->SetTextColor( crOldText ); pDC->SelectObject (pFont); //set it to the old font dispFont.DeleteObject (); } else { HBITMAP hBitmap =(HBITMAP) LoadImage (AfxGetInstanceHandle (),MAKEINTRESOURCE (m_idBitmap), IMAGE_BITMAP,0,0,LR_DEFAULTCOLOR|LR_LOADMAP3DCOLORS|LR_LOADTRANSPARENT); GetClientRect (rect); CDC memdc; CBitmap bmp; CBitmap *poldbmp; bmp.Attach (hBitmap); BITMAP bitmap; bmp.GetBitmap (&bitmap); memdc.CreateCompatibleDC( pDC ); // Select the bitmap into the DC poldbmp = (CBitmap *) memdc.SelectObject( &bmp ); // Copy (BitBlt) bitmap from memory DC to screen DC pDC -> StretchBlt( rect.left,rect.top, rect.right-rect.left, rect.bottom -rect.top, &memdc, 0,0,bitmap.bmWidth,bitmap.bmHeight, SRCCOPY ); memdc.SelectObject( poldbmp ); } ReleaseDC (pDC); } CButton::OnTimer(nIDEvent); } void CBtnMenu::SetBkgndColor (COLORREF rgb) { m_clrBack = rgb; if ((HBRUSH)m_brBackground != NULL) m_brBackground.DeleteObject(); m_brBackground.CreateSolidBrush (m_clrBack); } void CBtnMenu::SetTextColor (COLORREF rgb) { m_clrText = rgb; m_crText = m_clrText; } void CBtnMenu::SetCursor(UINT idCursor) { m_idCursor = idCursor; } void CBtnMenu::SetBitmap (UINT idBmp) { m_idBitmap = idBmp; }