在MFC控件中更改背景和标题的颜色 [英] Change color of background and title in MFC Control

查看:163
本文介绍了在MFC控件中更改背景和标题的颜色的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想为MFC应用程序中的编辑控件",静态控件"和按钮控件"更改文本颜色和背景颜色.该控件处于CDialogEx对话框中.

我尝试添加OnCtlColor(使用Visual Studio中的向导,在WM_CTLCOLR消息上),但是我无法设置may静态控件和按钮控件的颜色.

我还在IF构造中的OnCtlColor函数中也设置了一个断点,但是我什么也没收到.

我还尝试使用SetTextColor函数从GetDlgItem检索控件的句柄,但是我无法根据需要更改颜色.

请帮助我.

解决方案

我可以断言我曾尝试在CDialog中的OnCtlColor中使用它,并且它适用于静态控件和编辑控件.

所有您需要做的是:

  • 要更改背景色,您需要创建一个在该功能之外仍然存在的画笔,并使用返回它的HBRUSH.

    return (HBRUSH) m_brush.GetSafeHandle();

    因此,您必须创建一个成员或静态变量(此代码中为m_brush)(我建议使用第一个变量),并且在对话框初始化中必须创建所需的画笔.

    我认为也许某些控件对此不起作用,而对于那些我也做到了

    pDC->SetBkColor(RGB(0,0,255));

    但是似乎什么也没做;它在安全代码中.

  • 为了改变文字颜色,我做了

    pDC->SetTextColor(RGB(255,0,0));

这些体验对于编辑和静态操作效果很好,但对于组框却根本不起作用!

Groupbox在MFC中是一个奇怪的实体,有点像platyplus:它们是带有BS_GROUPBOXCButton,但是在此功能中,它的nCtlColorCTLCOLOR_STATIC而不是CTLCOLOR_BTN!我为他们做了

UINT nStyle = (UINT)(pWnd->GetStyle() & 0x0F);

if(nStyle == BS_GROUPBOX)
{
    return (HBRUSH) m_brush2.GetSafeHandle();
}

绘制的是组框标题后面的小矩形!

我无法更改组框的文本颜色!

如果您有组框,并且更改其标题的文本颜色确实很重要,则可以从 http://social.msdn.microsoft.com/Forums/vstudio/zh-CN/53f47162-078a-418f-8067-ee61a81ceeac/checkbox- transparent-color-not-working-in-vs2008?forum = vcgeneral ,我做了自己的Groupbox类,现在就像:

class CMyGroupBox: public CButton
{
protected:
    virtual void PreSubclassWindow()
    {
        SetWindowTheme(*this, _T(""), _T(""));
        #pragma comment(lib, "UxTheme.lib")
    }
};

我刚刚声明了其中一个,并使用了其各自的控件ID进行了DDX_Control的操作,现在我可以看到提供给SetTextColor的颜色的文本了.如果您为此控件返回HBRUSH,则绘制的是围绕组框标题绘制的未填充矩形.

更新2:我只是将CMyGroupBox概括为CMyButton,因为它不仅在组框中,还在复选框和按钮中都使用了PreSubClassWindow方法.在复选框中效果很好,在按钮中效果很好,我对此不太满意.

更新3:我试图消除对文本呈现的一些怪异效果,而我只是评论了pDC->SetBkColor(RGB(0,0,255));行;结果是在文本:(之后出现一个难看的矩形矩形.然后我用pDC->SetBkMode(TRANSPARENT);替换了它,我也看到了奇怪的效果:(

更新4:为了避免不得不将我的所有复选框,组框和按钮声明为包含PreSubClassWindow方法的类,我研究并发现不需要这样做.代码

SetThemeAppProperties(0);
#pragma comment(lib, "UxTheme.lib")
AfxGetMainWnd()->SendMessage(WM_THEMECHANGED, 0U, 0L);

在整个应用程序级别禁用所有控件的主题设置.

I want to change text color and background color for my EDIT CONTROL, STATIC CONTROL and BUTTON CONTROL in MFC application. The control is in a CDialogEx dialogue .

I try to add the OnCtlColor (with wizard in visual studio, on the WM_CTLCOLR message) but I can't set the color of may static control and button control.

I put also a break point in the OnCtlColor function (in the IF construct), but I don't receive anything.

I also tried to use the SetTextColor function retrieving the handle of the control from GetDlgItem, but I can't change the color as I want.

Pleas help me.

解决方案

I can assert that I tried to use in OnCtlColor in a CDialog and it worked for the static and for the edit controls.

All you have to do is:

  • For changing background color, you need to create a brush that still exists outside that function and return its HBRUSH with

    return (HBRUSH) m_brush.GetSafeHandle();

    So you have to make a variable (m_brush in this code) that is member or a static (I recommend the first), and in the dialog initialization you have to create the brush you want.

    I thought maybe some controls will not work with this, and for those I also did

    pDC->SetBkColor(RGB(0,0,255));

    But seems to do nothing; it is in the code for safety.

  • For changing the text color,I did

    pDC->SetTextColor(RGB(255,0,0));

These experiences worked well for edits and statics, but did not work at all for groupboxes!

Groupboxes are a strange entity in MFC, some kind of a platyplus: they are a CButton with the BS_GROUPBOX, but in this function, its nCtlColor is CTLCOLOR_STATIC instead of CTLCOLOR_BTN! I did this for them

UINT nStyle = (UINT)(pWnd->GetStyle() & 0x0F);

if(nStyle == BS_GROUPBOX)
{
    return (HBRUSH) m_brush2.GetSafeHandle();
}

and what got painted was the little rectangle behind the groupbox title!

I could not get the text colour of groupboxes changed!

If you have groupboxes and it is really important to change their titles' text color, you can get the one from http://www.codeproject.com/Articles/29016/XGroupBox-an-MFC-groupbox-control-to-display-text and get its essential code parts: to be derived from CStatic, the OnPaint() and DrawItem() methods. Do not forget also the ON_WM_PAINT() on the message map. I don't know if the OnEraseBkgnd() and its is ON_WM_ERASEBKGND() message mapping are so essential. It is also needed to change them to be Static text controls in the resources, declare a XGroupBox variable and do a DDX_Control of it. I tested it and it really works.

For buttons, with CButtons it did not work. But, for each button, I simply declared a CMFCButton variable in the class and did a DDX_Control of each one. After, I had two choices:

  • Set its m_bTransparent property to TRUE in the form constructor (search this variable on afxbutton.cpp file for reference) for the ones I wanted to have the same color as the form (I also painted the form; in my case I was implementing themes on an application)

  • Set the Background color with SetFaceColor() and set the Text Color with SetTextColor() in form initialization.

When the CMFCButton does not have these things set, it got its color from theme blending of the currently selected CMFCVisualManager.

Note: I also replaced my CSpinButton entities with CMFCSpinButon ones, because I wanted colors from the selected theme.

In the OnCtlColor, the nCtlColor variable is important because it will allow you to personalize different colors to different types, without testing dynamic_cast success or failure for every control.

Do not forget to add ON_WM_CTLCOLOR() to your message map.

UPDATE 1: After following the advice of the accepted answer on http://social.msdn.microsoft.com/Forums/vstudio/en-US/53f47162-078a-418f-8067-ee61a81ceeac/checkbox-transparent-color-not-working-in-vs2008?forum=vcgeneral , I did my own Groupbox class, and now it is like:

class CMyGroupBox: public CButton
{
protected:
    virtual void PreSubclassWindow()
    {
        SetWindowTheme(*this, _T(""), _T(""));
        #pragma comment(lib, "UxTheme.lib")
    }
};

I just declared one of this, and did DDX_Control with its respective control ID, and now I can see the text in the color I supplied to SetTextColor. If you return a HBRUSH for this control, what gets painted is a non-filled rectangle drawn around the groupbox's title.

UPDATE 2: I just generalized the CMyGroupBox to be CMyButton, for using its PreSubClassWindow method not only in groupboxes, but also in checkboxes and buttons. In checkboxes it works well, in buttons, I am not so satisfied with the results.

UPDATE 3: I was trying to remove some weird effect on the rendering of the text and I just commented the pDC->SetBkColor(RGB(0,0,255)); line; the result was an ugly while rectangle behind the text :( . Then I replaced it with pDC->SetBkMode(TRANSPARENT); and I also see tht weird effect :(

UPDATE 4: In order to avoid to have to declare all my checkboxes, groupboxes and buttons as the class that contains the PreSubClassWindow method, I researched and discovered that it is not needed to do it. The code

SetThemeAppProperties(0);
#pragma comment(lib, "UxTheme.lib")
AfxGetMainWnd()->SendMessage(WM_THEMECHANGED, 0U, 0L);

disables theming for all controls at the whole application level.

这篇关于在MFC控件中更改背景和标题的颜色的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆