自绘式按钮COwnerDrawBtn:可设置文本字体、文本颜色、按钮背景图片
2014-07-18 16:54
603 查看
使用MFC做界面的程序员,一定很痛苦,因为其默认效果比较古老呆板,实现好的UI效果往往需要费大力气
但是花了精力去做,收获比起只是拖拖界面设置参数的程序员,自然是更多的,最重要的收获,就是灵活和自由,
到最后发现想要什么效果,都可以去自定义实现
最近需要自绘按钮,需求是:能设置背景图、能设置字体、能改文本颜色,
上网找到的都不能完全满足,最后参照着自己实现了一个,经验证可用,贴代码:
OwnerDrawBtn.h
但是花了精力去做,收获比起只是拖拖界面设置参数的程序员,自然是更多的,最重要的收获,就是灵活和自由,
到最后发现想要什么效果,都可以去自定义实现
最近需要自绘按钮,需求是:能设置背景图、能设置字体、能改文本颜色,
上网找到的都不能完全满足,最后参照着自己实现了一个,经验证可用,贴代码:
//使用示例 COwnerDrawBtn m_btn; m_btn.MoveWindow(xGap,yGap,BTN_W,BTN_H); m_btn.SetBkSkin(_T("res\\Btn.bmp")); m_btn.SetTextFont(120, "宋体"); m_btn.SetTextColor(RGB(255,0,0));
OwnerDrawBtn.h
#ifndef _OWNERDRAW_BTN_H_ #define _OWNERDRAW_BTN_H_ #if _MSC_VER > 1000 #pragma once #endif class COwnerDrawBtn : public CButton { public: COwnerDrawBtn(); virtual ~COwnerDrawBtn(); private: enum{ BS_NORMAL=0, BS_HOVER, BS_PUSHDOWN, BS_DISABLE }; int m_nStatus; //按钮状态 BOOL m_bInRect; //鼠标进入标志 CString m_strText; //按钮文字 COLORREF m_BackColor; //背景色 COLORREF m_TextColor; //文本颜色 CRect m_BtnRect; //按钮尺寸 CFont m_font; //字体 HBITMAP m_hBkBmp; //背景图片 public: void DrawButton(CDC *pDC); //画按钮 void DrawBkBmp(CDC *pDC); void DrawTxt(CDC *pDC); void SetText(CString str); void SetTextColor(COLORREF color); //设置文本颜色 void SetBkColor(COLORREF color); //设置背景颜色 void SetTextFont(int FontHight,LPCTSTR FontName); //设置字体 void SetTextFont(CFont* pFont); void SetBkSkin(HBITMAP hBkBmp); //设置按钮底图,传(五态)图片句柄 void SetBkSkin(LPCTSTR pBmpFile); //传相对exe路径 //{{AFX_VIRTUAL(COwnerDrawBtn) virtual void PreSubclassWindow(); virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct); //}}AFX_VIRTUAL protected: //{{AFX_MSG(COwnerDrawBtn) afx_msg void OnMouseMove( UINT nFlags, CPoint point); afx_msg void OnLButtonDown( UINT nFlags, CPoint point ); afx_msg void OnLButtonUp( UINT nFlags, CPoint point ); //}}AFX_MSG DECLARE_MESSAGE_MAP() }; #endifOwnerDrawBtn.cpp
#include "stdafx.h" #include "OwnerDrawBtn.h" #pragma comment(lib,"msimg32.lib") #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif COwnerDrawBtn::COwnerDrawBtn() { m_nStatus = BS_NORMAL; m_bInRect = FALSE; m_strText = _T(""); m_TextColor = RGB(0,0,0); m_BackColor = RGB(243,243,243); m_hBkBmp = NULL; } COwnerDrawBtn::~COwnerDrawBtn() { } BEGIN_MESSAGE_MAP(COwnerDrawBtn, CButton) //{{AFX_MSG_MAP(COwnerDrawBtn) ON_WM_MOUSEMOVE() ON_WM_LBUTTONDOWN() ON_WM_LBUTTONUP() //}}AFX_MSG_MAP END_MESSAGE_MAP() // PreSubclassWindow()在按钮创建前自动执行,所以我们可以在其中做一些初始工作,此处为按钮设置属性“自绘” void COwnerDrawBtn::PreSubclassWindow() { ModifyStyle( 0, BS_OWNERDRAW ); //设置按钮属性为自绘 CButton::PreSubclassWindow(); } // DrawItem()函数是一个关键函数,按钮的绘制工作就在这里进行,它的作用相当于对话框中的OnPaint()函数和视图中的OnDraw()函数 // 这里做了三项工作:获取按钮尺寸、获取按钮文本、绘制按钮。其中绘制工作在自定义函数DrawButton()中完成 void COwnerDrawBtn::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct) { m_BtnRect = lpDrawItemStruct->rcItem; //获取按钮尺寸 if( m_strText.IsEmpty() ) GetWindowText( m_strText ); //获取按钮文本 CDC *pDC = CDC::FromHandle( lpDrawItemStruct->hDC ); int nSaveDC = pDC->SaveDC(); if (pDC) { DrawButton( pDC ); //绘制按钮 pDC->RestoreDC( nSaveDC ); } } void COwnerDrawBtn::DrawButton(CDC *pDC) { if(BS_DISABLE == m_nStatus) m_nStatus = BS_NORMAL; //状态 if( GetStyle() & WS_DISABLED ) m_nStatus = BS_DISABLE; DrawBkBmp(pDC); //绘制按钮背景 DrawTxt(pDC); //绘制按钮文字 } void COwnerDrawBtn::DrawBkBmp(CDC *pDC) { if (m_hBkBmp) { int nWidth=m_BtnRect.Width(); int nHeight=m_BtnRect.Height(); HDC hBkDC = CreateCompatibleDC(pDC->m_hDC); HBITMAP hOld = (HBITMAP)::SelectObject(hBkDC, m_hBkBmp); int bmpLeft = 0; if (BS_HOVER == m_nStatus) bmpLeft = nWidth*3; else if (BS_PUSHDOWN == m_nStatus) bmpLeft = nWidth; else if (BS_DISABLE == m_nStatus) bmpLeft = nWidth*2; TransparentBlt(pDC->m_hDC,0,0,nWidth,nHeight, hBkDC, bmpLeft,0,nWidth,nHeight, RGB(255,0,255)); ::SelectObject(hBkDC,hOld); ::DeleteDC(hBkDC); } else { COLORREF clrBorder; switch( m_nStatus ) { case BS_NORMAL: clrBorder = RGB(192,192,192); break; case BS_HOVER: clrBorder = RGB(255,255,255); break; case BS_PUSHDOWN: clrBorder = RGB(192,192,192); break; case BS_DISABLE: clrBorder = RGB(243,243,243); break; } CBrush Brush; Brush.CreateSolidBrush( m_BackColor ); //背景刷 pDC->SelectObject( &Brush ); CPen Pen; Pen.CreatePen(PS_SOLID, 1, clrBorder ); pDC->SelectObject( &Pen ); pDC->RoundRect(&m_BtnRect,CPoint(5,5)); //画圆角矩形 if( m_nStatus!=BS_PUSHDOWN)//绘制按钮按下时的边框 { CRect Rect; Rect.SetRect( m_BtnRect.left+2, m_BtnRect.top+1, m_BtnRect.right, m_BtnRect.bottom ); pDC->DrawEdge( &Rect, BDR_RAISEDINNER, BF_RECT ); //画边框 } if( GetFocus()==this )//绘制拥有焦点按钮的虚线框 { CRect Rect; Rect.SetRect( m_BtnRect.left+3, m_BtnRect.top+2, m_BtnRect.right-3, m_BtnRect.bottom-2 ); pDC->DrawFocusRect( &Rect ); } } } void COwnerDrawBtn::DrawTxt(CDC *pDC) { COLORREF txtColor; switch( m_nStatus ) { case BS_NORMAL: txtColor = m_TextColor; break; case BS_HOVER: txtColor = m_TextColor; break; case BS_PUSHDOWN: txtColor = m_TextColor; break; case BS_DISABLE: txtColor = GetSysColor(COLOR_GRAYTEXT); break; } pDC->SetTextColor( txtColor ); pDC->SetBkMode( TRANSPARENT ); pDC->DrawText( m_strText, &m_BtnRect, DT_SINGLELINE | DT_CENTER | DT_VCENTER | DT_END_ELLIPSIS); } void COwnerDrawBtn::OnMouseMove(UINT nFlags, CPoint point) { if( !m_bInRect || GetCapture()!=this ) //鼠标进入按钮 { m_bInRect = TRUE; //设置进入标志 SetCapture(); //捕获鼠标 m_nStatus = BS_HOVER; //设置按钮状态 Invalidate(); //重绘按钮 } else { if (m_bInRect && !m_BtnRect.PtInRect(point)) //鼠标离开按钮 { m_bInRect = FALSE; //清除进入标志 ReleaseCapture(); //释放鼠标 m_nStatus = BS_NORMAL; //设置按钮状态 Invalidate(); //重绘按钮 } } CButton::OnMouseMove(nFlags, point); } void COwnerDrawBtn::OnLButtonDown(UINT nFlags, CPoint point) { m_nStatus = BS_PUSHDOWN; Invalidate(); //重绘按钮 CButton::OnLButtonDown(nFlags, point); } void COwnerDrawBtn::OnLButtonUp(UINT nFlags, CPoint point) { m_nStatus = BS_HOVER; Invalidate(); //重绘按钮 CButton::OnLButtonUp(nFlags, point); } void COwnerDrawBtn::SetText(CString str) { m_strText = _T(""); SetWindowText(str); } void COwnerDrawBtn::SetTextColor(COLORREF color) { m_TextColor = color; Invalidate(); } void COwnerDrawBtn::SetBkColor(COLORREF color) { m_BackColor = color; Invalidate(); } void COwnerDrawBtn::SetTextFont(int FontHight,LPCTSTR FontName) { m_font.DeleteObject(); m_font.CreatePointFont(FontHight, FontName); SetFont(&m_font); } void COwnerDrawBtn::SetTextFont(CFont* pFont) { SetFont(pFont); } void COwnerDrawBtn::SetBkSkin(HBITMAP hBkBmp) { if (!m_hBkBmp) { m_hBkBmp = hBkBmp; } } void COwnerDrawBtn::SetBkSkin(LPCTSTR pBmpFile) { if (!m_hBkBmp) { m_hBkBmp = (HBITMAP)LoadImage(AfxGetInstanceHandle(), pBmpFile, IMAGE_BITMAP,0,0,LR_LOADFROMFILE|LR_CREATEDIBSECTION); } }
相关文章推荐
- 黄聪:phpexcel中文教程-设置表格字体颜色背景样式、数据格式、对齐方式、添加图片、批注、文字块、合并拆分单元格、单元格密码保护
- MFC 可以设置背景色、字体、字体颜色、透明背景的 Static 静态文本控件
- iOS中设置导航栏的背景颜色和标题字体以及颜色,以及tabBarItem的图片和字体颜色的设置
- 设置导航栏背景颜色及文本字体大小
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- PHPExcel-设置表格字体颜色背景样式、数据格式、对齐方式、添加图片、批注、文字块、合并拆分单元格、单元格密码保护
- html设置按钮背景颜色与背景图片一样,即设置按钮背景透明
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- phpexcel中文教程-设置表格字体颜色背景样式、数据格式、对齐方式、添加图片、批注、文字块、合并拆分单元格、单元格密码保护
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- ExtJS4.1.1 设置表格背景颜色 修改文本颜色 在表格中插入图片
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- phpexcel中文教程-设置表格字体颜色背景样式、数据格式、对齐方式、添加图片、批注、文字块、合并拆分单元格、单元格密码保护
- IOS设置导航栏全局的背景图片、导航栏title文字颜色大小、导航栏左右按钮的颜色。
- ios自定义导航navigation,设置navigation的背景图,navigation左边按钮,以及navigation字体颜色
- MFC中设置静态文本的字体颜色、背景透明以及解决字体重叠
- MFC 可以设置背景色、字体、字体颜色、透明背景的 Static 静态文本控件
- phpexcel中文教程-设置表格字体颜色背景样式、数据格式、对齐方式、添加图片、批注、文字块、合并拆分单元格、单元格密码保护
- ExtJS4.1.1 设置表格背景颜色 修改文本颜色 在表格中插入图片