您的位置:首页 > 其它

MFC 可以设置背景色、字体、字体颜色、透明背景的 Static 静态文本控件

2015-07-07 08:56 831 查看
转自:http://blog.csdn.net/cashey1991/article/details/7545614

MFC库里没有符合这个条件的控件,于是我自己写了一个,初步测试有效。

注:可以设置透明背景,但还不能做到透明度设置(如50%透明度)

如果设置了背景色,就不保留透明背景

默认背景色是透明的

[cpp] view
plaincopy





// 设置背景色(若clr为CLR_NONE,则背景透明)

void SetBackgroundColor(COLORREF clr){m_clrBackground = clr;}

// 设置文字前景色

void SetTextColor(COLORREF clr){m_clrText = clr;}

// 设置文字字体

void SetFont(CString strFaceName, LONG nHeight);

如何使用:
1.先将RichStatic.h和RichStatic.cpp添加入工程

2.对话框添加Static控件后,增加一个控件变量,类型设置为CRichStatic(或手动添加,在对话框类DoDataExchange中添加DDX_Control)

源码:

[cpp] view
plaincopy





#pragma once





// CRichStatic



class CRichStatic : public CStatic

{

DECLARE_DYNAMIC(CRichStatic)



public:

CRichStatic();

virtual ~CRichStatic();



protected:

afx_msg BOOL OnEraseBkgnd(CDC* pDC);

afx_msg LRESULT OnSetText(WPARAM,LPARAM);

DECLARE_MESSAGE_MAP()

virtual void PreSubclassWindow();



private:

COLORREF m_clrText; // 文字前景色

COLORREF m_clrBackground; // 文字背景色

CFont *m_pTextFont; // 文字字体

CBitmap m_Bmp; // 保存背景用的位图对象

BOOL m_selfCreated;

public:

// 设置背景色(若clr为CLR_NONE,则背景透明)

void SetBackgroundColor(COLORREF clr){m_clrBackground = clr;}

// 设置文字前景色

void SetTextColor(COLORREF clr){m_clrText = clr;}

// 设置文字字体

void SetFont(CString strFaceName, LONG nHeight);



public:

virtual void DrawItem(LPDRAWITEMSTRUCT /*lpDrawItemStruct*/);

};

[cpp] view
plaincopy





// RichStatic.cpp : 实现文件

//





#include "stdafx.h"

#include "RichStatic.h"









// CRichStatic





IMPLEMENT_DYNAMIC(CRichStatic, CStatic)





CRichStatic::CRichStatic():

m_clrText(0), m_clrBackground(CLR_NONE), m_hFont(NULL), m_selfCreated(FALSE),

m_xAlignment(X_LEFT), m_yAlignment(Y_TOP)

{





}





CRichStatic::~CRichStatic()

{

if (m_selfCreated && m_hFont != NULL)

{

DeleteObject(m_hFont); // 若字体对象为对象自己创建并且不为NULL,则销毁掉以释放内核对象

}

}









BEGIN_MESSAGE_MAP(CRichStatic, CStatic)

ON_MESSAGE(WM_SETTEXT,OnSetText)

ON_WM_ERASEBKGND()

END_MESSAGE_MAP()













// CRichStatic 消息处理程序





void CRichStatic::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)

{

if (m_clrBackground != CLR_NONE) // 若背景色不为CLR_NONE(CLR_NONE表示无背景色),则绘制背景

{

RECT rect;

GetWindowRect(&rect);

CBrush brush;

brush.CreateSolidBrush(m_clrBackground);

::SelectObject(lpDrawItemStruct->hDC, brush.m_hObject); // 设置画刷颜色

::SelectObject(lpDrawItemStruct->hDC, GetStockObject(NULL_PEN)); // 设置笔为空笔(不绘制边界)

Rectangle(lpDrawItemStruct->hDC, 0, 0,rect.right - rect.left, rect.bottom - rect.top);

}





CString strCaption; // 标题文字

GetWindowText(strCaption);

if (m_hFont != NULL)

{

::SelectObject(lpDrawItemStruct->hDC, m_hFont);

}





// 计算输出字串的横纵坐标

int x = 0, y = 0;

if (X_LEFT != m_xAlignment || Y_TOP != m_yAlignment) // 不是左对齐或不是顶对齐

{

CDC *pDC = CDC::FromHandle(lpDrawItemStruct->hDC);

CRect crect;

GetWindowRect(&crect);

CSize size = pDC->GetTextExtent(strCaption);

if (X_RIGHT == m_xAlignment) // 右对齐

{

x = crect.Width() - size.cx;

}

else if (X_CENTER == m_xAlignment) // X居中对齐

{

x = (crect.Width()- size.cx) / 2;

}





if (Y_BOTTOM == m_yAlignment) // 顶对齐

{

y = crect.Height() - size.cy;

}

else if (Y_CENTER == m_yAlignment) // Y居中对齐

{

y = (crect.Height() - size.cy) / 2;

}

}

// 设置dc字串颜色

::SetTextColor(lpDrawItemStruct->hDC, m_clrText);

TextOut(lpDrawItemStruct->hDC, x, y, strCaption, strCaption.GetLength());

}





void CRichStatic::PreSubclassWindow()

{

CStatic::PreSubclassWindow();

ModifyStyle(0, SS_OWNERDRAW);

}





void CRichStatic::SetFont(CString strFaceName, LONG nHeight)

{

if (m_selfCreated && m_hFont != NULL)

{

DeleteObject(m_hFont); // 若字体对象为对象自己创建并且不为NULL,则销毁掉以释放内核对象

}

CFont cfont;

LOGFONT lf;

memset(&lf, 0, sizeof lf); // 清空LOGFONT结构体,之后对其赋值

lf.lfHeight = nHeight;

_tcscpy_s(lf.lfFaceName, strFaceName.GetBuffer()); // 将字体名拷贝到LOGFONT结构体中

VERIFY(cfont.CreateFontIndirect(&lf)); // 创建新的字体

m_hFont = (HFONT)cfont.m_hObject;

m_selfCreated = TRUE; // 标记字体为自己创建的

}





void CRichStatic::SetFont(HFONT hFont)

{

if (m_selfCreated && m_hFont != NULL)

{

DeleteObject(m_hFont); // 若字体对象为对象自己创建并且不为NULL,则销毁掉以释放内核对象

}

m_hFont = hFont;

m_selfCreated = FALSE; // 标记字体非自己创建

}





void CRichStatic::SetFont(const CFont *pFont)

{

if (m_selfCreated && m_hFont != NULL)

{

DeleteObject(m_hFont); // 若字体对象为对象自己创建并且不为NULL,则销毁掉以释放内核对象

}

m_hFont = (HFONT)pFont->m_hObject;

m_selfCreated = FALSE; // 标记字体非自己创建

}





BOOL CRichStatic::OnEraseBkgnd(CDC* pDC)

{

// 当背景色为透明时,需要保存与拷贝显示主框的显示区域

if (m_clrBackground == CLR_NONE)

{

if (m_Bmp.GetSafeHandle() == NULL)

{

CRect Rect;

GetWindowRect(&Rect);

CWnd *pParent = GetParent();

ASSERT(pParent);

pParent->ScreenToClient(&Rect); // 将坐标转换为与主对话框相对应



// 拷贝对应区域主框显示的内容

CDC *pDC = pParent->GetDC();

CDC MemDC;

MemDC.CreateCompatibleDC(pDC);

m_Bmp.CreateCompatibleBitmap(pDC,Rect.Width(),Rect.Height());

CBitmap *pOldBmp = MemDC.SelectObject(&m_Bmp);

MemDC.BitBlt(0,0,Rect.Width(),Rect.Height(),pDC,Rect.left,Rect.top,SRCCOPY);

MemDC.SelectObject(pOldBmp);

MemDC.DeleteDC(); // 删除内存DC,否则内存泄漏

pParent->ReleaseDC(pDC);

}

else // 将主框显示的内容拷贝回去

{

CRect Rect;

GetClientRect(Rect);

CDC MemDC;

MemDC.CreateCompatibleDC(pDC);

CBitmap *pOldBmp = MemDC.SelectObject(&m_Bmp);

pDC->BitBlt(0,0,Rect.Width(),Rect.Height(),&MemDC,0,0,SRCCOPY);

MemDC.SelectObject(pOldBmp);

MemDC.DeleteDC(); // 删除内存DC,否则内存泄漏

}

}





return TRUE;

}





LRESULT CRichStatic::OnSetText(WPARAM wParam,LPARAM lParam)

{

LRESULT Result = Default();

Invalidate();

UpdateWindow();

return Result;

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: