VC改变对话框按钮字体颜色和背景的解决方案
要想修改CButton类按钮背景颜色和文字颜色,必须利用自绘方法对按钮进行重新绘制。
这可以通过定义一个以CButton为基类的新按钮类来实现。
以下为具体的实现方法:方法一:加入一个新类,类名:CMyButton,基类:CButton。
在头文件MyButton.h 中加入以下变量和函数定义:private:int m_Style; //按钮形状(0-正常,1-当前,2-按下,3-锁定)BOOL b_InRect; //鼠标进入标志CString m_strText; //按钮文字COLORREF m_ForeColor; //文本颜色COLORREF m_BackColor; //背景色COLORREF m_LockForeColor; //锁定按钮的文字颜色CRect m_ButRect; //按钮尺寸CFont* p_Font; //字体void DrawButton(CDC *pDC); //画正常的按钮// 接口函数public:void SetText(CString str);void SetForeColor(COLORREF color); //设置文本颜色void SetBkColor(COLORREF color); //设置背景颜色void SetTextFont(int FontHight,LPCTSTR FontName); //设置字体在MyButton.cpp 的构造函数中初始化变量:CMyButton::CMyButton(){m_Style = 0; //按钮形状风格b_InRect = false; //鼠标进入标志m_strText = _T(""); //按钮文字(使用默认文字)m_ForeColor = RGB(0,0,0); //文字颜色(黑色)m_BackColor = RGB(243,243,243); //背景色(灰白色)m_LockForeColor = GetSysColor(COLOR_GRAYTEXT); //锁定按钮的文字颜色p_Font = NULL; //字体指针}用ClassWizard添加下列消息函数:PreSubclassWindow();DrawItem();onMouse Move();OnLButtonDown();OnLButtonUp();在各函数内加入代码:void CMyButton::PreSubclassWindow(){ModifyStyle( 0, BS_OWNERDRAW ); //设置按钮属性为自画式CButton::PreSubclassWindow();}PreSubclassWindow()在按钮创建前自动执行,所以我们可以在其中做一些初始工作。
这里我只做了一项工作,就是为按钮设置属性为“自绘”式,这样,用户在添加按钮后,就不需设置“Owner draw”属性了。
void CMyButton::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct){CDC *pDC = CDC::FromHandle( lpDrawItemStruct->hDC );m_ButRect = lpDrawItemStruct->rcItem; //获取按钮尺寸if( m_strText.IsEmpty() )GetWindowText( m_strText ); //获取按钮文本int nSavedDC = pDC->SaveDC();VERIFY( pDC );DrawButton( pDC ); //绘制按钮pDC->RestoreDC( nSavedDC );}DrawItem()函数是一个关键函数,按钮的绘制工作就在这里进行,它的作用相当于对话框中的OnPaint()函数和视图中的OnDraw()函数。
这里我做了三项工作:获取按钮尺寸、获取按钮文本、绘制按钮。
其中绘制工作在自定义函数DrawButton()中完成。
以下就是绘制过程:void CMyButton::DrawButton(CDC *pDC){//调整状态if( m_Style==3 ) m_Style = 0;if( GetStyle() & WS_DISABLED )m_Style = 3; //禁止状态//根据状态调整边框颜色和文字颜色COLORREF bColor, fColor; //bColor为边框颜色,fColor为文字颜色switch( m_Style ){case 0: bColor = RGB(192,192,192); fColor = m_ForeColor; break; //正常按钮case 1: bColor = RGB(255,255,255); fColor = m_ForeColor; break; //鼠标进入时按钮case 2: bColor = RGB(192,192,192); fColor = m_ForeColor; break; //按下的按钮case 3: bColor = m_BackColor; fColor = m_LockForeColor; break; //锁定的按钮}//绘制按钮背景CBrush Brush;Brush.CreateSolidBrush( m_BackColor ); //背景刷pDC->SelectObject( &Brush );CPen Pen;Pen.CreatePen(PS_SOLID, 1, bColor );pDC->SelectObject( &Pen );pDC->RoundRect(&m_ButRect,CPoint(5,5)); //画圆角矩形//绘制按钮按下时的边框if( m_Style!=2 ){CRect Rect;Rect.SetRect( m_ButRect.left+2, m_ButRect.top+1, m_ButRect.right, m_ButRect.bottom );pDC->DrawEdge( &Rect, BDR_RAISEDINNER, BF_RECT ); //画边框}//绘制按钮文字pDC->SetTextColor( fColor ); //画文字pDC->SetBkMode( TRANSPARENT );pDC->DrawText( m_strText, &m_ButRect, DT_SINGLELINE | DT_CENTER | DT_VCENTER | DT_END_ELLIPSIS);//绘制拥有焦点按钮的虚线框if( GetFocus()==this ){CRect Rect;Rect.SetRect( m_ButRect.left+3, m_ButRect.top+2, m_ButRect.right-3, m_ButRect.bottom-2 );pDC->DrawFocusRect( &Rect ); //画拥有焦点的虚线框}}变量m_Style 表征当前按钮状态,它的取值为:0-正常,1-当前,2-按下,3-锁定。
不同状态下按钮的边框颜色和文字颜色有所不同。
m_Style 的值在鼠标响应函数中进行修改。
绘制工作主要利用CDC类的绘图函数完成,主要注意在m_Style 不同取值下表现出来的差别。
void CMyButton::onMouse Move(UINT nFlags, CPoint point){if( !b_InRect || GetCapture()!=this ) //鼠标进入按钮{b_InRect = true; //设置进入标志SetCapture(); //捕获鼠标m_Style = 1; //设置按钮状态Invalidate(); //重绘按钮}else{if ( !m_ButRect.PtInRect(point) ) //鼠标离开按钮{b_InRect = false; //清除进入标志ReleaseCapture(); //释放捕获的鼠标m_Style = 0; //设置按钮状态Invalidate(); //重绘按钮}}CButton::onMouse Move(nFlags, point);}onMouse Move()函数是鼠标移动消息函数,用于判定当前鼠标指针是否在按钮上。
b_InRect 是个标志,为true表示鼠标指针进入了按钮区域,此时要捕获鼠标,让鼠标命令传送给按钮。
当鼠标指针离开按钮时,要清除b_InRect标志,并且释放捕获的鼠标,让其它窗口可以接收鼠标命令。
Invalidate()函数用于更新按钮,它会自动调用DrawItem()函数重新绘制按钮。
设置条件的目的是仅在鼠标指针进入按钮和离开按钮时更新按钮,这样可以防止鼠标在按钮上移动时发生闪烁。
void CMyButton::OnLButtonDown(UINT nFlags, CPoint point){m_Style = 2;Invalidate(); //重绘按钮CButton::OnLButtonDown(nFlags, point);}OnLButtonDown()函数是单击鼠标左键时的消息函数。
这里只是重新绘制按钮,具体的单击响应应该在拥有按钮的对话框或视图中进行。
void CMyButton::OnLButtonUp(UINT nFlags, CPoint point){m_Style = 1;Invalidate(); //重绘按钮CButton::OnLButtonUp(nFlags, point);}OnLButtonUp()函数是单击鼠标左键后弹起时的消息函数。
这里也只是重绘按钮,这样能使按钮在按下和弹起时有所不同,使按钮看上去有动态效果。
接口函数是用CMyButton类定义的按钮修改颜色、字体和按钮文字的接口,由以下函数组成://设置按钮文本void CMyButton::SetText(CString str){m_strText = _T("");SetWindowText(str);}//设置文本颜色void CMyButton::SetForeColor(COLORREF color){m_ForeColor = color;Invalidate();}//设置背景颜色void CMyButton::SetBkColor(COLORREF color){m_BackColor = color;Invalidate();}//设置字体(字体高度、字体名)void CMyButton::SetTextFont(int FontHight,LPCTSTR FontName){if ( p_Font ) delete p_Font; //删除旧字体p_Font = new CFont;p_Font->CreatePointFont( FontHight, FontName ); //创建新字体SetFont( p_Font ); //设置字体}由于新字体由new 生成,必须显式回收,这项工作可以在CMyButton类的析构函数中进行:CMyButton::~CMyButton(){if ( p_Font ) delete p_Font; //删除字体}这样一个可设置颜色、字体的按钮类就做好了。
VC第10讲自定义控件(如更改控件背景颜色、图片、形状等)
步骤三:导入按钮位图,这里四幅图大小要一致,使用 CBitmapButton::LoadBitmaps装载各种状态的图片,使用 CBitmapButton::SizeToContent函数使按钮适合图片大小。
SND_NOSTOP PlaySound不打断原来的声音播出并立即返回FALSE。 SND_NOWAIT 如果驱动程序正忙则函数就不播放声音并立即返回。
SND_PURGE 停止所有与调用任务有关的声音。若参数pszSound为NULL, 就停止所有的声音,否则,停止pszSound指定的声音。
SND_RESOURCE pszSound参数是WAVE资源的标识符,这时要用到hmod 参数。
SND_SYNC 同步播放声音,在播放完后PlYSTEM 如果是背景窗口,当这个标志被设置,声音是分配到音频会议系 统通知的声音。系统音量控制程序(sndvol)显示音量滑块控制系统通知的声音。 设置该标志将下控制音量滑块。如果没有设置该标志,声音是分配到默认的音 频会议的应用进程。
特殊效果按钮-示例 1 9 0 6
n m_num0.LoadBitmaps(IDB_BITMAP2,IDB_BITMAP1); //载入 n m_num0.SizeToContent(); //使按钮适应图片大小
背景颜色改变
19 0 6
n CPaintDC dc(this); // 用于绘制的设备上下文 n CRect rect; n GetClientRect(&rect);
fdwSound用来指定播放模式,参数如下:
VC++更改对话框背景色和字体颜色
VC++更改对话框背景色和字体颜色方法一:设置所有窗口的颜色MFC程序修改对话框的背景和文字颜色最简单的方法就是调用SetDialogBkColor函数,SetDialogBkColor是CWinApp类的成员函数,以下是该函数的原型:void CWinApp::SetDialogBkColor(COLORREF clrCtlBk, COLORREF clrCtlText);请注意,SetDialogBkColor函数并不是对Windows的某个API 的封装,他是MFC框架的一部分,所以不使用MFC的程序也就不能享受这种方便。
这个函数的使用很简单,在程序的CWinApp派生类的InitInstance函数中,添加一行代码就行了,写在domodal()的上一句:SetDialogBkColor(RGB(188,197,230),RGB(13,125,188));注:前一个为背景色,后一个为字体颜色。
方法二:设置当前窗口改变对话框的背景颜色的原理很简单,就是响应WM_ERASEBKGND消息,用自定义的颜色填充对话框的客户区背景,代替对话框窗口默认的背景填充动作。
改变控件和字体的颜色同理,是响应WM_CTLCOLOR这一消息。
具体操作,方法如下:首先://消息映射BEGIN_MESSAGE_MAP(CHelloDlg, CDialog)//{{AFX_MSG_MAP(CHelloDlg)ON_WM_SYSCOMMAND()ON_WM_PAINT()ON_WM_CTLCOLOR() //字体颜色ON_WM_ERASEBKGND() //背景色ON_WM_QUERYDRAGICON()//}}AFX_MSG_MAPEND_MESSAGE_MAP()其次:定义两个函数afx_msg BOOL OnEraseBkgnd(CDC* pDC);afx_msg HBRUSH OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor);第三:重载OnEraseBkgnd和OnCtlColor其中预先定义:protected:CBrush m_brBkgnd;//设置对话框背景色方法一:可以实现(但有点问题)BOOL CHelloDlg::OnEraseBkgnd(CDC* pDC){CRect rect;GetClientRect(&rect);m_brBkgnd.CreateSolidBrush(RGB(183,213,213)); //背景色pDC->FillRect(&rect,&m_brBkgnd);return TRUE;}方法二:可行BOOL CClientDlg::OnEraseBkgnd(CDC* pDC){CBrush back(RGB(220,215,254));CBrush* pold=pDC->SelectObject(&back);CRect rect;pDC->GetClipBox (&rect);pDC->PatBlt(rect.left,rect.top,rect.Width(),rect.Height(),PATCOPY);pDC->SelectObject(pold);return TRUE;方法三:也可行BOOL CHelloDlg::OnEraseBkgnd(CDC* pDC){CBrush MyBrush;MyBrush.CreateSolidBrush(RGB(0,255,0));CBrush *pOldBrush=pDC->SelectObject(&MyBrush);CRect Rect;GetClientRect(&Rect);pDC->Rectangle(&Rect);pDC->SelectObject(pOldBrush);return TRUE;}//设置对话框中控件的字体颜色HBRUSH CHelloDlg::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor){HBRUSH hbr = CDialog::OnCtlColor(pDC, pWnd, nCtlColor);if(pWnd->GetDlgCtrlID() == IDC_EDIT_MULLINE) //多行edit 控件{pDC->SetT extColor(RGB(13,125,188)); //设置字体颜色return hbr;}else{pDC->SetBkMode(TRANSPARENT);pDC->SetT extColor(RGB(255,125,188));return (HBRUSH)m_brBkgnd; //因为CBrush类实现了HBRUSH 类型转换操作符}。
MFC中改变对话框背景的几个消息函数的调用顺序、VC
MFC中改变对话框背景的几个消息函数的调用顺序、VC设置对话框背景颜色及背景图片可在OnCtlColor(),OnEraseBkgnd(),OnPaint()里设置,对话框初始化完毕,显示时调用OnSize()-OnEraseBkgnd(),-OnPaint()-OnCtlColor(),若想改变对话框大小,比如全屏显示ShowWindow(SW_SHOWMAXIMIZED);UpdateWindow();其中ShowWindow会调用OnSize()-OnEraseBkgnd(),UpdateWindow();调用OnPaint()-OnCtlColor(),若对话框中没有设置消息响应OnEraseBkgnd(),,则系统默认消息响应OnEraseBkgnd()会调用OnCtlColor()设置对话框背景(即替代OnEraseBkgnd())对话框的背景设置可在OnCtlColor()中进行,因为OnCtlColor()一般会被多次调用,所以要想设置的CFont,CBrush等应在OnInitDialog中初始化,若要在OnCtlColor()中设置,在设置前先调用Detach就可以了,如下示例HBRUSH CDb3Dlg:OnCtlColor(CDC*pDC,CWnd*pWnd,UINT nCtlColor){if(pWnd-GetDlgCtrlID()==IDC_STATIC5){m_font.CreatePointFont(300,"宋体");pDC-SelectObject(&m_font);m_font.Detach();pDC-SetBkMode(TRANSPARENT);return(HBRUSH):GetStockObject(NULL_BRUSH);}}但是如果在OnCtlColor()在设置背景图片,则图片不会随对话框大小按比例缩放所以可调用StretchBlt()函数设置,如下示例:void CDb3Dlg:OnPaint(){CClientDC cdc(this);CDC comdc;comdc.CreateCompatibleDC(&cdc);CBitmap bitmap;bitmap.LoadBitmap(IDB_BITMAP2);comdc.SelectObject(&bitmap);CRect rect;GetClientRect(rect);BITMAP bit;bitmap.GetBitmap(&bit);cdc.StretchBlt(0,0,rect.Width(),rect.Height(),&comdc,0,0,bit.bmWi dth,bit.bmHeight,SRCCOPY);}//全屏显示对话框背景图片(限bmp格式)用了两年的VC,其实对OnPaint的工作原理一直都是一知半解。
VC设置对话框背景色、背景图片、背景音乐
一、设置背景颜色的三种方法:1、我们知道程序在运行的时候会调用OnPain函数,那么我们可以在这里设置背景颜色。
void CFlipCardsDlg::OnPaint(){if (IsIconic()){//保持不变}else{CRect rc;GetClientRect( &rc );// 获取客户区CPaintDC dc(this);dc.FillSolidRect(&rc, RGB(0,160,0)); // 填充客户区颜色CDialog::OnPaint();}}2、第二种方法只要一条语句,但是这里要注意这里绘制的颜色是针对程序中所有的对话框(如果是单文档的话,好像不行)SetDialogBkColor(RGB(0,0,255),RGB(255,0,0));// 前一个RGB是背景色,后一RGB是文本颜色该函数放在工程的APP文件的初始化函数中。
3、第三种方法,利用ClassWizard 重载OnCtlColor(),即WM_CTLCOLOR消息在要着色的对话框中申明一个变量,CBRUSH m_hbrush;然后在项目的Dlg类初始化函数中给m_hbrush赋值。
m_brush.CreateSolidBrush(RGB(0, 255, 0));然后在OnCtlColor(...)返回该画刷就可以了,如下。
HBRUSH CFlipCardsDlg::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor) {HBRUSH hbr = CDialog::OnCtlColor(pDC, pWnd, nCtlColor);// TODO: Change any attributes of the DC hereswitch (nCtlColor){case CTLCOLOR_DLG:HBRUSH aBrush;aBrush = CreateSolidBrush(RGB(0, 150, 0));hbr = aBrush;break;}// TODO: Return a different brush if the default is not desiredreturn hbr;}这样为对话框着色就可以实现了。
VC设置对话框背景
VC设置对话框背景少将2014-11-20VC对话框默认的灰度背景实在是不美观,填充背景图成了改善用户界面的一个很好的选择。
首先在资源视图中添加一个位图资源,如命名为IDB_BMPBK。
在对话框中添加OnEraseBkgnd()事件处理函数,用于擦除背景进行重绘。
其中添加的代码如下:BOOL DialogClass::OnEraseBkgnd(CDC* pDC){//创建内存DCCDC MemDC;//CBitmap对象CBitmap Bitmap,*pOldBitmap;//BITMAP句柄BITMAP bm;//加载位图Bitmap.LoadBitmap(IDB_BMPBK);//将位图资源与句柄绑定Bitmap.GetObject(sizeof(BITMAP),&bm);//创建与内存兼容的DCMemDC.CreateCompatibleDC(pDC);//替换原位图pOldBitmap=(CBitmap*)(MemDC.SelectObject(&Bitmap));//获取绘制的区域CRect rcClient;GetClientRect(&rcClient);//绘制到客户区pDC->BitBlt(0,0,rcClient.Width(),rcClient.Height(),&MemDC,0,0,SRCCOPY);MemDC.SelectObject(pOldBitmap);MemDC.DeleteDC();return TRUE;}默认生成的OnEraseBkgnd()处理函数会有调用基类的处理函数然后再返回结果,要注意把这一句直接删除,然后直接返TRUE。
VC改变对话框按钮字体颜色和背景的解决方案
要想修改CButton类按钮背景颜色和文字颜色,必须利用自绘方法对按钮进行重新绘制。
这可以通过定义一个以CButton为基类的新按钮类来实现。
以下为具体的实现方法:方法一:加入一个新类,类名:CMyButton,基类:CButton。
在头文件MyButton.h 中加入以下变量和函数定义:private:int m_Style; //按钮形状(0-正常,1-当前,2-按下,3-锁定)BOOL b_InRect; //鼠标进入标志CString m_strText; //按钮文字COLORREF m_ForeColor; //文本颜色COLORREF m_BackColor; //背景色COLORREF m_LockForeColor; //锁定按钮的文字颜色CRect m_ButRect; //按钮尺寸CFont* p_Font; //字体void DrawButton(CDC *pDC); //画正常的按钮// 接口函数public:void SetText(CString str);void SetForeColor(COLORREF color); //设置文本颜色void SetBkColor(COLORREF color); //设置背景颜色void SetTextFont(int FontHight,LPCTSTR FontName); //设置字体在MyButton.cpp 的构造函数中初始化变量:CMyButton::CMyButton(){m_Style = 0; //按钮形状风格b_InRect = false; //鼠标进入标志m_strText = _T(""); //按钮文字(使用默认文字)m_ForeColor = RGB(0,0,0); //文字颜色(黑色)m_BackColor = RGB(243,243,243); //背景色(灰白色)m_LockForeColor = GetSysColor(COLOR_GRAYTEXT); //锁定按钮的文字颜色p_Font = NULL; //字体指针}用ClassWizard添加下列消息函数:PreSubclassWindow();DrawItem();onMouse Move();OnLButtonDown();OnLButtonUp();在各函数内加入代码:void CMyButton::PreSubclassWindow(){ModifyStyle( 0, BS_OWNERDRAW ); //设置按钮属性为自画式CButton::PreSubclassWindow();}PreSubclassWindow()在按钮创建前自动执行,所以我们可以在其中做一些初始工作。
vc根据字体对话框和颜色对话框设置控件里的字体和颜色
vc 根据字体对话框和颜色对话框设置控件里的字体和颜色vc 根据字体对话框和颜色对话框设置控件里的字体和颜色2009-05-23 10:13:25| 分类:VC&MFC|字号订阅视频教程及其源码下载地址/source/780472 题目:编写一个基于对话框的应用程序,要求其能实现如下功能:(1)可以用来打开及显示文本文件。
(2)可以设置所显示的文本的字体颜色。
★打开Microsoft Visual C++ 6.0 文件->新建选择MFC AppWizard(exe) 输入工程文件名。
这里填写09 点击确定按钮,程序将自动出现MFC应用程序向导选择基本对话框点击完成按钮出现新建工程信息对话框。
点击确定按钮★★★★首先是定义颜色类★★★★★ ★点工具栏->插入->类name 任意填写这里填的是CStatic09 Base class选择CStatic 点击确定按钮。
★鼠标切换左边的类视图区出现09 classes 鼠标左键双击CStatic09 左边将出现N行代码找到class My09Static : public CStatic { // Construction public: My09Static(); 。
在下面输入:private: COLORREF m_ForeColor; //文本颜色COLORREF m_BackColor; //背景色CBrushm_BkBrush; //背景刷public: voidSetForeColor(COLORREF color);//设置文本颜色void SetBkColor(COLORREF color);//设置背景颜色找到protected: //{{AFX_MSG(My09Static) // NOTE - the ClassWizard will add and remove member functions here. /}}AFX_MSG DECLARE_MESSAGE_MAP() 在中间加入afx_msg HBRUSH CtlColor(CDC* pDC, UINT nCtlColor);//消息响应函数效果如下:protected://{{AFX_MSG(My09Static) // NOTE - the ClassWizard will add and remove member functions here. afx_msg HBRUSH CtlColor(CDC* pDC, UINT nCtlColor);//消息响应函数/}}AFX_MSG DECLARE_MESSAGE_MAP() ★点击CStatic09左边的+号按钮出现CStatic09() 右键双击CStatic09() 左边将出现N行代码找到CStatic09::CStatic09() { } 在大括号与小括号之间输入://文字颜色m_ForeColor =GetSysColor( COLOR_BTNTEXT ); //背景色m_BackColor = GetSysColor( COLOR_BTNFACE ); //背景刷m_BkBrush.CreateSolidBrush(m_BackColor); 找到BEGIN_MESSAGE_MAP(My09Static, CStatic)//{{AFX_MSG_MAP(My09Static) // NOTE - the ClassWizard will add and remove mapping macros here. //}}AFX_MSG_MAP END_MESSAGE_MAP() 在中间输入ON_WM_CTLCOLOR_REFLECT()//颜色宏定义效果如下BEGIN_MESSAGE_MAP(My09Static, CStatic)//{{AFX_MSG_MAP(My09Static) // NOTE - the ClassWizard will add and remove mapping macros here. ON_WM_CTLCOLOR_REFLECT()//颜色宏定义//}}AFX_MSG_MAP END_MESSAGE_MAP() 最后找到///////////////////////////////////////////////////////////////////////////// // CStatic09 message handlers 在下面输入HBRUSH CStatic09::CtlColor(CDC* pDC, UINT nCtlColor){ pDC->SetTextColor( m_ForeColor );pDC->SetBkColor( m_BackColor ); return (HBRUSH)m_BkBrush.GetSafeHandle(); } void CStatic09::SetForeColor(COLORREF color) //设置文本颜色{ m_ForeColor = color; } voidCStatic09::SetBkColor(COLORREF color) //设置背景颜色{ m_BackColor = color; m_BkBrush.Detach();m_BkBrush.CreateSolidBrush( m_BackColor ); } 设置对话框代码找到类视图中的CMu09Dlg,双击后显示代码。
如何更改MFC按钮的背景色
今天打算给自己写的工程上点色。
但是在给按钮上色的时候出了点问题。
在网上找的方法基本上都不管用。
说得跟真的一样,各种OnCtrlColor()和OnEraseBkground(),各种技术帝的方法看起来都很厉害,但是都不管用。
真正有用的办法是自定义button,才能实现按钮颜色。
但是这个办法不免有些复杂,我这么懒的人,既不想为这么个小功能去重写一个类,也不想使用第三方的按钮类,所以只能另辟蹊径了。
所幸在codeproject上又找到了一个大神写的教程。
使用CMFCButton便可以实现这种功能。
接下来简单介绍一下CMFCButton的用法。
建立一个基于对话框的工程MFCButtonTest。
在对话框编辑界面中,拖入一个button控件,改资源ID号为IDC_BUTTON_TEST。
接下来,在CMFCButtonTestDlg::OnInitDialog()中添加如下代码:CMFCButton * button = new CMFCButton;button->Create(_T("Test Button"),WS_VISIBLE,CRect(5, 5, 80, 50),this,IDC_BUTTON_TEST);注意!!这个行为是错误的,会有内存泄漏,只为写个例子,真实工程中不允许这种写法。
好了,运行一下吧,会看到屏幕上出现了两个按钮。
但是不用担心,TestButton就是Button1,Button1就是TestButton,他们共享同一个资源号。
也可以说TestButton其实是Button1的“影分身”,在对话框编辑界面中是看不到的。
那么解决方案就简单啦,在对话框编辑界面中把Button1的Visible属性设为False便可以了。
Tips: 这样一来,可以创建多个CMFCButton,都使用同一个ID号,那么他们可以分散在世界各地,而且还能运行同一段代码,真够帅气!再次运行。
WM_CTLCOLOR和OnCtlColor消息的用法
WM_CTLCOLOR和OnCtlColor消息的用法很多人都觉得自己的程序的界面不那么美观,往往VC默认产生的对话框比较单调,因此很多人往往找到很多其它的控件对对话框进行美化修饰,例如给静态控件设置字体,设置背景颜色等等,其实这些完全可以由VC自己的WM_CTLCOLOR消息来完成!WM_CTLCOLOR消息用来完成对EDIT、STATIC、BUTTON等控件设置背景和字体颜色,其用法如下:1.首先在自己需要设置界面的对话框上点击右键-->建立类向导-->加入WM_CTLCOLOR消息-->自动生成OnCtlColor()函数,此函数可以对本对话框的控件的界面外观做修饰,用法如下:将类向导产生的函数做如下修改:HBRUSH CDialogColor::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor){HBRUSH hbr = CDialog::OnCtlColor(pDC,pWnd, nCtlColor);// TODO: Change any attributes of theDC here//设置显示字体CFont * cFont=new CFont;cFont->CreateFont(16,0,0,0,FW_SEMIBOLD,FALSE,FALSE,0,ANSI_CHARSET,OUT_DEFAULT_PRECIS,CLIP_DEFAULT_PRECIS,DEFAULT_QUALITY,DEFAULT_PITCH&FF_SWISS,"Arial");//对特定的控件做修改switch(nCtlColor){case CTLCOLOR_STATIC: //对所有静态文本控件的设置{pDC->SetBkMode(TRANSPARENT);//设置背景为透明pDC->SetTextColor(RGB(255,255,0)); //设置字体颜色pWnd->SetFont(cFont); //设置字体HBRUSH B = CreateSolidBrush(RGB(125,125,255));//创建画刷return (HBRUSH) B; //返回画刷句柄}case CTLCOLOR_EDIT: //对所有编辑框的设置{pDC->SetBkMode(TRANSPARENT);pDC->SetTextColor(RGB(255,255,0));pWnd->SetFont(cFont);HBRUSH B = CreateSolidBrush(RGB(125,125,255));return (HBRUSH) B;}default:return CDialog::OnCtlColor(pDC,pWnd, nCtlColor);}}注:case的类别有以下几种:CTLCOLOR_BTN 按钮控件CTLCOLOR_DLG 对话框CTLCOLOR_EDIT 编辑框CTLCOLOR_LISTBOX 列表框CTLCOLOR_MSGBOX 消息框CTLCOLOR_SCROLLBAR 滚动条CTLCOLOR_STATIC 静态文本2.你可能觉得对所有的控件使用统一的界面设置觉得不自由,其实VC同样可以对特定的ID 的控件进行设置,方法如下:switch (pWnd->GetDlgCtrlID()){//针对ID为IDC_CTL1、IDC_CTL2和IDC_CTL3的控件进行同样的设置case IDC_CTL1:case IDC_CTL2:case IDC_CTL3:{pDC->SetBkMode(TRANSPARENT);pDC->SetTextColor(RGB(255,255, 0));pWnd->SetFont(cFont);HBRUSH B = CreateSolidBrush(RGB(125,125,255));return (HBRUSH) B;}default:return CDialog::OnCtlColor(pDC, pWnd, nCtlColor);}通过消息WM_CTLCOLOR我们可以改变对话框或一些特殊控件的背景颜色1、添加WM_CTLCOLOR消息映射。
VC 按钮颜色设置
这是一个实现自绘CButton的类,期望对大家有点帮助,我提供这个类,只是为大家提供一个自绘控件的思路,你可以在此基础上,随意地修改代码,直到它能完成你所需要的功能.其它控件的自绘,原理了和这个差不多.1.#if !defined(AFX_BUTTONST_H__1271FF9C_E28C_4D3B_B429_AFE65924A5D0__INCLUDED_)2.#define AFX_BUTTONST_H__1271FF9C_E28C_4D3B_B429_AFE65924A5D0__INCLUDED_3.4.#if _MSC_VER > 10005.#pragma once6.#endif // _MSC_VER > 10007.// ButtonST.h : header file8.//9.10.///////////////////////////////////////////////////////////////////////////// 11.// CButtonST window 12.13.class CButtonST : public CButton14.{15.// Construction 16.public:17. CButtonST();18.19.// Attributes 20.public:21.22.// Operations 23.public:24. //设置背景颜色25. void SetBkColor(COLORREF BkColor);26. //设置鼠标在按钮上的偏移颜色27. void SetShOffset(int nShOffset);28. //设置字体颜色29. void SetTextColor(COLORREF TextColor);30. //设置网页链接31. void SetURL(CString strURL);32. //设置背景图片33. void SetBkPicture(CBitmap *pBitMap);34.35.// Overrides 36. // ClassWizard generated virtual function overrides 37. //{{AFX_VIRTUAL(CButtonST) 38. public:39. virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);40. virtual BOOL Create(LPCTSTR lpszClassName, LPCTSTR lpszWindowName, DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID, CCreateContext* pContext = NULL);41. protected:42. virtual BOOL PreCreateWindow(CREATESTRUCT& cs);43. virtual void PreSubclassWindow();44. //}}AFX_VIRTUAL 45.46.// Implementation 47.public:48. virtual ~CButtonST();49.50. void DrawItem1(LPDRAWITEMSTRUCT lpDrawItemStruct);51.52. // Generated message map functions 53.protected:54. //{{AFX_MSG(CButtonST) 55. afx_msg void OnMouseMove(UINT nFlags, CPoint point);56. afx_msg BOOL OnNcActivate(BOOL bActive);57. afx_msg void OnNcMouseMove(UINT nHitTest, CPoint point);58. afx_msg void OnKillFocus(CWnd* pNewWnd);59. afx_msg void OnLButtonDown(UINT nFlags, CPoint point);60. //}}AFX_MSG 61.protected:62. //鼠标是否在按钮上面63. BOOL m_IsPressed;64. COLORREF m_BkColor;65. int m_nShOffset;66. COLORREF m_TextColor;67. CString m_strURL;68. CBitmap *m_pBitMapBK;69.protected:70. //背景颜色偏移71. COLORREF OffsetColor(COLORREF color,int nOffset);72. //鼠标离开73. LRESULT OnMouseLeave(WPARAM wParam, LPARAM lParam);74. DECLARE_MESSAGE_MAP()75.};76.77.///////////////////////////////////////////////////////////////////////////// 78.79.//{{AFX_INSERT_LOCATION}} 80.// Microsoft Visual C++ will insert additional declarations immediately before the previous line. 81.82.#endif // !defined(AFX_BUTTONST_H__1271FF9C_E28C_4D3B_B429_AFE65924A5D0__INCLUDED_) 83.1.// ButtonST.cpp : implementation file2.//3.4.#include "stdafx.h"5.#include "ContrlST.h"6.#include "ButtonST.h"7.8.#ifdef _DEBUG9.#define new DEBUG_NEW 10.#undef THIS_FILE 11.static char THIS_FILE[] = __FILE__; 12.#endif 13.#define BS_TYPEMASK SS_TYPEMASK 14.15.///////////////////////////////////////////////////////////////////////////// 16.// CButtonST 17.18.CButtonST::CButtonST()19.{20. m_IsPressed = FALSE;21. m_BkColor = RGB(216,233,216);22. m_nShOffset = 30;23. m_TextColor = RGB(0,0,0);24. m_strURL = "";25. m_pBitMapBK = NULL;26.}27.28.CButtonST::~CButtonST()29.{30. if(m_pBitMapBK!=NULL)31. {32. delete m_pBitMapBK;33. m_pBitMapBK = NULL;34. }35.}36.37.38.BEGIN_MESSAGE_MAP(CButtonST, CButton)39. //{{AFX_MSG_MAP(CButtonST) 40. ON_WM_MOUSEMOVE()41. ON_WM_NCACTIV ATE()42. ON_WM_NCMOUSEMOVE()43. ON_WM_KILLFOCUS()44. ON_MESSAGE(WM_MOUSELEA VE, OnMouseLeave)45. ON_WM_LBUTTONDOWN()46. //}}AFX_MSG_MAP 47.END_MESSAGE_MAP()48.49.///////////////////////////////////////////////////////////////////////////// 50.// CButtonST message handlers 51.52.53.//设置背景颜色54.void CButtonST::SetBkColor(COLORREF BkColor)55.{56. m_BkColor = BkColor;57. this->Invalidate();58.}59.//设置鼠标在按钮上的偏移颜色60.void CButtonST::SetShOffset(int nShOffset)61.{62. m_nShOffset = nShOffset;63. this->Invalidate();64.}65.//设置字体颜色66.void CButtonST::SetTextColor(COLORREF TextColor)67.{68. m_TextColor = TextColor;69. this->Invalidate();70.}71.//设置网页链接72.void CButtonST::SetURL(CString strURL)73.{74. m_strURL = strURL;75.}76.77.//设置背景图片78.void CButtonST::SetBkPicture(CBitmap *pBitMap)79.{80. if(m_pBitMapBK==pBitMap)81. return;82. if(m_pBitMapBK!=NULL)83. {84. delete m_pBitMapBK;85. m_pBitMapBK = pBitMap;86. }87. m_pBitMapBK = pBitMap;88. this->Invalidate();89.}90.//背景颜色偏移91.COLORREF CButtonST::OffsetColor(COLORREF color,int nOffset)92.{93. BYTE byRed = 0;94. BYTE byGreen = 0;95. BYTE byBlue = 0;96. short shOffsetR = nOffset;97. short shOffsetG = nOffset;98. short shOffsetB = nOffset;99. if (nOffset < -255 || nOffset > 255)100. {101. nOffset = 30;102. }103.104. // Get RGB components of specified color 105. byRed = GetRValue(color);106. byGreen = GetGV alue(color);107. byBlue = GetBValue(color);108.109. // Calculate max. allowed real offset 110. if (nOffset > 0)111. {112. if (byRed + nOffset > 255) shOffsetR = 255 - byRed;113. if (byGreen + nOffset > 255) shOffsetG = 255 - byGreen;114. if (byBlue + nOffset > 255) shOffsetB = 255 - byBlue;115. nOffset = min(min(shOffsetR, shOffsetG), shOffsetB);116. }117. else118. {119. if (byRed + nOffset < 0) shOffsetR = -byRed;120. if (byGreen + nOffset < 0) shOffsetG = -byGreen;121. if (byBlue + nOffset < 0) shOffsetB = -byBlue;122.123. nOffset = max(max(shOffsetR, shOffsetG), shOffsetB);124. }125. int r,g,b;126. r = byRed + nOffset;127. g =byGreen + nOffset;128. b =byBlue + nOffset;129. return RGB(r,g,b);130.}131.132.void CButtonST::DrawItem1(LPDRAWITEMSTRUCT lpDrawItemStruct)133.{134. // TODO: Add your code to draw the specified item 135.136.137. CDC* pDC = CDC::FromHandle(lpDrawItemStruct->hDC);138. CRect rect = lpDrawItemStruct->rcItem;139. CRect offRect = rect;140. int ndist = 2;141. offRect.left+= ndist;142. offRect.right -=ndist;143. offRect.top += ndist;144. offRect.bottom -=ndist;145.146.147. pDC->SetBkMode(TRANSPARENT);148. pDC->SetTextColor(m_TextColor);149.150. //绘制背景151. if(m_pBitMapBK!=NULL)152. {153. CDC* pNewDC = new CDC;154. pNewDC->CreateCompatibleDC(pDC);155. pNewDC->SelectObject(m_pBitMapBK);156. BITMAP bmp;157. m_pBitMapBK->GetBitmap(&bmp);158. if(m_IsPressed)159. {160. pDC->StretchBlt(0,0,rect.Width(),rect.Height(),pNewDC,0,0,bmp.bmWidth,bmp.bmHeight,SRCCOPY);161. }162. else163. {164. CBrush brush(RGB(220,220,220));//RGB(m_nShOffset,m_nShOffset,m_nShOffset)); 165. pDC->FillRect(&rect,&brush); 166. pDC->StretchBlt(0,0,rect.Width(),rect.Height(),pNewDC,0,0,bmp.bmWidth,bmp.bmHeight,SRCAND);167. }168.169. delete pNewDC;170. pNewDC = NULL;171. }172. else173. {174. if(m_IsPressed)175. {176. CBrush brush(OffsetColor(m_BkColor,m_nShOffset));177. pDC->FillRect(rect,&brush);178. CBrush brush1(RGB(128,128,128));179. pDC->FrameRect(rect,&brush1);180. pDC->FrameRect(offRect,&brush1);181. }182. else183. {184. CBrush brush(m_BkColor);185. pDC->FillRect(rect,&brush);186. CBrush brush1(RGB(128,128,128));187. pDC->FrameRect(offRect,&brush1);188. }189. }190.191.192. CString sTitle;193. GetWindowText(sTitle);194. offRect.OffsetRect(0,rect.Height()/2-8);195. // pDC->DrawText(sTitle, sTitle.GetLength(),offRect, DT_WORDBREAK | DT_CENTER); 196. pDC->DrawText(sTitle, sTitle.GetLength(),offRect, DT_WORDBREAK|DT_CENTER);197.198.199.}200.201.void CButtonST::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)202.{203. // TODO: Add your code to draw the specified item204. DrawItem1(lpDrawItemStruct);205. return;206.207.208. CDC* pDC = CDC::FromHandle(lpDrawItemStruct->hDC);209. CRect rect = lpDrawItemStruct->rcItem;210. CRect offRect = rect;211. int ndist = 2;212. offRect.left+= ndist;213. offRect.right -=ndist;214. offRect.top += ndist;215. offRect.bottom -=ndist;216.217. CDC* pResetDC=new CDC();218. pResetDC->CreateCompatibleDC(pDC);219. CBitmap bitmap;220. bitmap.CreateCompatibleBitmap(pDC,rect.Width(),rect.Height());221. pResetDC->SelectObject(&bitmap);222.223.224. pResetDC->SetBkMode(TRANSPARENT);225. pResetDC->SetTextColor(m_TextColor);226.227. //绘制背景228. if(m_pBitMapBK!=NULL)229. {230. CDC* pNewDC = new CDC;231. pNewDC->CreateCompatibleDC(pResetDC);232. pNewDC->SelectObject(m_pBitMapBK);233. BITMAP bmp;234. m_pBitMapBK->GetBitmap(&bmp);235. if(m_IsPressed)236. {237. pResetDC->StretchBlt(0,0,rect.Width(),rect.Height(),pNewDC,0,0,bmp.bmWidth,bmp.bmHeight,SRCCOPY);238. }239. else240. {241. CBrush brush(RGB(220,220,220));//RGB(m_nShOffset,m_nShOffset,m_nShOffset)); 242. pResetDC->FillRect(&rect,&brush);243. pResetDC->StretchBlt(0,0,rect.Width(),rect.Height(),pNewDC,0,0,bmp.bmWidth,bmp.bmHeight,SRCAND);244. }245.246. delete pNewDC;247. pNewDC = NULL;248. }249. else250. {251. if(m_IsPressed)252. {253. CBrush brush(OffsetColor(m_BkColor,m_nShOffset));254. pResetDC->FillRect(rect,&brush);255. CBrush brush1(RGB(128,128,128));256. pResetDC->FrameRect(rect,&brush1);257. pResetDC->FrameRect(offRect,&brush1);258.259. }260. else261. {262. CBrush brush(m_BkColor);263. pResetDC->FillRect(rect,&brush);264. CBrush brush1(RGB(128,128,128));265. pResetDC->FrameRect(offRect,&brush1);266. }267. }268.269.270. CString sTitle;271. GetWindowText(sTitle);272. offRect.OffsetRect(0,rect.Height()/2-8);273.// pDC->DrawText(sTitle, sTitle.GetLength(),offRect, DT_WORDBREAK | DT_CENTER); 274. pResetDC->DrawText(sTitle, sTitle.GetLength(),offRect, DT_CENTER);275. pDC->StretchBlt(0,0,rect.Width(),rect.Height(),pResetDC,0,0,rect.Width(),rect.Height(),SRCCOPY);276. delete pResetDC;277.}278.279.void CButtonST::OnMouseMove(UINT nFlags, CPoint point)280.{281. // TODO: Add your message handler code here and/or call default 282. TRACKMOUSEEVENT csTME;283. csTME.cbSize = sizeof(csTME);284. csTME.dwFlags = TME_LEA VE;285. csTME.hwndTrack = m_hWnd;286. ::_TrackMouseEvent(&csTME);287.288. if(m_IsPressed==FALSE)289. {290. m_IsPressed = TRUE;291. this->Invalidate();292. }293.294. CButton::OnMouseMove(nFlags, point);295.}296.297.BOOL CButtonST::OnNcActivate(BOOL bActive)298.{299. // TODO: Add your message handler code here and/or call default 300.301. return CButton::OnNcActivate(bActive);302.}303.304.void CButtonST::OnNcMouseMove(UINT nHitTest, CPoint point)305.{306. // TODO: Add your message handler code here and/or call default 307.308.309. CButton::OnNcMouseMove(nHitTest, point);310.}311.312.void CButtonST::OnKillFocus(CWnd* pNewWnd)313.{314. CButton::OnKillFocus(pNewWnd);315. // TODO: Add your message handler code here 316.}317.LRESULT CButtonST::OnMouseLeave(WPARAM wParam, LPARAM lParam)318.{319. m_IsPressed = FALSE;320. this->Invalidate();321. return 0;322.} // End of OnMouseLeave 323.324.325.BOOL CButtonST::Create(LPCTSTR lpszClassName, LPCTSTR lpszWindowName, DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID, CCreateContext* pContext)326.{327. // TODO: Add your specialized code here and/or call the base class 328. dwStyle |= BS_OWNERDRAW;329. return CWnd::Create(lpszClassName, lpszWindowName, dwStyle, rect, pParentWnd, nID, pContext);330.}331.332.void CButtonST::OnLButtonDown(UINT nFlags, CPoint point)333.{334. // TODO: Add your message handler code here and/or call default 335.336. if(m_strURL.IsEmpty()==FALSE)337. {338. SHELLEXECUTEINFO csSEI;339.340. memset(&csSEI, 0, sizeof(csSEI));341. csSEI.cbSize = sizeof(SHELLEXECUTEINFO);342. csSEI.fMask = SEE_MASK_FLAG_NO_UI;343. csSEI.lpVerb = _T("open");344. csSEI.lpFile = m_strURL;345. csSEI.nShow = SW_SHOWMAXIMIZED;346. ::ShellExecuteEx(&csSEI);347. }348. CButton::OnLButtonDown(nFlags, point);349.}350.351.BOOL CButtonST::PreCreateWindow(CREATESTRUCT& cs)352.{353. // TODO: Add your specialized code here and/or call the base class 354.355. return CButton::PreCreateWindow(cs);356.}357.358.void CButtonST::PreSubclassWindow()359.{360. // TODO: Add your specialized code here and/or call the base class 361. ModifyStyle(BS_TYPEMASK, BS_OWNERDRAW, SWP_FRAMECHANGED);362. CButton::PreSubclassWindow();363.}本文来自CSDN博客,转载请标明出处:/luo_sen/archive/2008/08/01/2751752.aspx。
