MFC-CListCtrl重绘,添加按钮到单元格

MFC Listctrl 不支持单元格颜色设置,以及单击其中某一单元格时高亮显示,要想达成自己的目的,就只能对其重绘。

关于单元格中按钮的添加,说一下思路,首先要重写CButton类,将其单击事件接口进行重写,这里就是发送自定义消息,到主窗口界面进行响应,然后在要生添加按钮的单元格中生成新的按钮,加入链表中进行存放,同时记录对应的单元格的行列信息,然后在单元格进行重绘时,改变button 位置即可,有个问题就是当listcontrol的大小发生变化时,因为重绘的原因,按钮的位置移动会有明显痕迹,暂时没想出什么好的办法解决,先这么用着吧。

资源链接:下载

其中listcontrol的单元格颜色,字体设置,部分来源网络,如有侵权,联系删除。

CListCtrlBtn.h


#define  WM_BNLOOK_CLICK  WM_USER + 100
#define  WM_BNCHECK_CLICK  WM_USER + 101

class CListCtrlBtn :public CButton
{

	DECLARE_DYNAMIC(CListCtrlBtn)
public:
	CListCtrlBtn();
	CListCtrlBtn(int type, int nItem, int nSubItem, CRect rect, HWND hParent);
	~CListCtrlBtn();
protected:
	DECLARE_MESSAGE_MAP()
public:
	virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
	afx_msg void OnBnClicked();
	int m_inItem;
	int m_inSubItem;
	CRect m_rect;
	HWND m_hParent;
	int  m_type;//按钮类型 用于处理消息 区分按钮信息
	BOOL bEnable;
};

CListCtrlBtn.cpp

#include "stdafx.h"
#include "ListCtrlBtn.h"

IMPLEMENT_DYNAMIC(CListCtrlBtn, CButton)
CListCtrlBtn::CListCtrlBtn()
{
}

CListCtrlBtn::CListCtrlBtn(int type,int nItem, int nSubItem, CRect rect, HWND hParent)    //-
{
	
	m_type = type;
	m_inItem = nItem;
	m_inSubItem = nSubItem;
	m_rect = rect;
	m_hParent = hParent;
	bEnable = TRUE;
}

CListCtrlBtn::~CListCtrlBtn()
{
}

BEGIN_MESSAGE_MAP(CListCtrlBtn, CButton)
	ON_CONTROL_REFLECT(BN_CLICKED, &CListCtrlBtn::OnBnClicked)
END_MESSAGE_MAP()

void CListCtrlBtn::OnBnClicked()
{
	// TODO: 在此添加控件通知处理程序代码
	if(m_type == 0)//表示查看
	::SendMessage(m_hParent, WM_BNLOOK_CLICK, m_inItem, m_inSubItem);
	if (m_type == 1)//表示巡检
	::SendMessage(m_hParent, WM_BNCHECK_CLICK, m_inItem, m_inSubItem);
}
void CListCtrlBtn::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
{
	ASSERT(lpDrawItemStruct);

	//以下为常态按钮绘制
	//TRACE("* Drawing: %08x\n", lpDrawItemStruct->itemState);
	CString sCaption;
	CDC *pDC = CDC::FromHandle(lpDrawItemStruct->hDC);	// get device context
	RECT r = lpDrawItemStruct->rcItem;					// context rectangle
	int cx = r.right - r.left;						// get width
	int cy = r.bottom - r.top;						// get height
	// get text box position
	RECT tr = { r.left + 2, r.top, r.right - 2, r.bottom };

	GetWindowText(sCaption);							// get button text
	pDC->SetBkMode(TRANSPARENT);

	// Select the correct skin 
	if (lpDrawItemStruct->itemState & ODS_DISABLED)//鼠标禁用
	{	
		// no skin selected for disabled state -> standard button 
		pDC->FillSolidRect(&r, GetSysColor(COLOR_BTNFACE));
		
		pDC->SetTextColor(GetSysColor(COLOR_GRAYTEXT));//)m_TextColor灰色字体  文字偏移
		OffsetRect(&tr, -1, -1);
		pDC->DrawText(sCaption, &tr, DT_SINGLELINE | DT_VCENTER | DT_CENTER);
	}
	else
	{										// SELECTED (DOWN) BUTTON
		if ((lpDrawItemStruct->itemState & ODS_SELECTED) )//当按下按钮时的处理
		{
			// no skin selected for selected state -> standard buttonRGB(255,152,0)
			pDC->FillSolidRect(&r,  RGB(39,169,241));//GetSysColor(COLOR_BTNFACE)
	
		}
		else
		{											// DEFAULT BUTTON
			pDC->FillSolidRect(&r,GetSysColor(COLOR_BTNFACE));//
		}
		// paint the enabled button text
		//pDC->SetTextColor(RGB(255,255,255));
		CFont nFont, *nOldFont;
		nFont.CreatePointFont(90, _T("微软雅黑"));//创建字体 
		nOldFont = pDC->SelectObject(&nFont);

		DrawText(lpDrawItemStruct->hDC, sCaption, sCaption.GetLength(), &tr, DT_SINGLELINE | DT_VCENTER | DT_CENTER);
		pDC->SelectStockObject(SYSTEM_FONT);
		//pDC->DrawText(sCaption, &tr, DT_SINGLELINE | DT_VCENTER | DT_CENTER);
	}
}

如上 对按钮的按键操作进行了重绘,改变了按钮的正常颜色,按下的事件颜色,以及字体。

 CHeaderCtrlCl.h   (表头设置)

#pragma once


class CHeaderCtrlCl : public CHeaderCtrl
{
	DECLARE_DYNAMIC(CHeaderCtrlCl)

public:
	CHeaderCtrlCl();
	virtual ~CHeaderCtrlCl();

protected:
	DECLARE_MESSAGE_MAP()
public:
	afx_msg void OnPaint();
	CStringArray m_HChar;
	CString m_Format; //表示对齐类型的整型数组,0表示左对齐,1表示中间对齐,2表示右对齐
public:
	int m_R;
	int m_G;
	int m_B;
	int m_Gradient;	// 画立体背景,渐变系数
	float m_Height;  //表头高度,这是倍数,
	int m_fontHeight; //字体高度
	int m_fontWith;   //字体宽度
	COLORREF m_color;
	LRESULT OnLayout( WPARAM wParam, LPARAM lParam );
};


 CHeaderCtrlCl.cpp

// HeaderCtrlCl.cpp : 实现文件
//

#include "stdafx.h"
#include "HeaderCtrlCl.h"


// CHeaderCtrlCl

IMPLEMENT_DYNAMIC(CHeaderCtrlCl, CHeaderCtrl)

CHeaderCtrlCl::CHeaderCtrlCl()
: m_R(171)
, m_G(199)
, m_B(235)
, m_Gradient(8)
{
	m_Format = "";
	m_Height = 1;
	m_fontHeight = 15;
	m_fontWith = 0;
	m_color = RGB(0,0,0);
}

CHeaderCtrlCl::~CHeaderCtrlCl()
{
}


BEGIN_MESSAGE_MAP(CHeaderCtrlCl, CHeaderCtrl)
	ON_WM_PAINT()
	ON_MESSAGE(HDM_LAYOUT, OnLayout)
END_MESSAGE_MAP()



// CHeaderCtrlCl 消息处理程序



void CHeaderCtrlCl::OnPaint()
{
	CPaintDC dc(this); // device context for painting
	// TODO: 在此处添加消息处理程序代码
	// 不为绘图消息调用 CHeaderCtrl::OnPaint()
	int nItem; 
	nItem = GetItemCount();//得到有几个单元 
	for(int i = 0; i<nItem;i ++) 
	{ 
		CRect tRect;
		GetItemRect(i,&tRect);//得到Item的尺寸
		int R = m_R,G = m_G,B = m_B;
		
		CRect nRect(tRect);//拷贝尺寸到新的容器中 
		nRect.left++;//留出分割线的地方 

		CRgn rgn1;
		RECT tr = { nRect.left-1, nRect.top, nRect.right, nRect.bottom};
		rgn1.CreateRectRgnIndirect(&tr);

		//内嵌窗体颜色绘制
		CBrush brush1(RGB(R, G, B));
		dc.FillRgn(&rgn1, &brush1);

		//内嵌窗体边框绘制
		CBrush brush2(RGB(209, 209, 209));
		dc.FrameRgn(&rgn1, &brush2, 1, 1);

		brush1.DeleteObject(); //释放画刷
		brush2.DeleteObject(); //释放画刷 


		绘制立体背景 
		//for(int j = tRect.top;j<=tRect.bottom;j++) 
		//{ 
		//	nRect.bottom = nRect.top+1; 
		//	CBrush _brush; 
		//	_brush.CreateSolidBrush(RGB(R,G,B));//创建画刷 
		//	dc.FillRect(&nRect,&_brush); //填充背景 
		//	_brush.DeleteObject(); //释放画刷 
		//	R-=m_Gradient;G-=m_Gradient;B-=m_Gradient;
		//	if (R<0)R = 0;
		//	if (G<0)G = 0;
		//	if (B<0)B= 0;
		//	nRect.top = nRect.bottom; 
		//} 
		dc.SetBkMode(TRANSPARENT);
		CFont nFont ,* nOldFont; 
		//dc.SetTextColor(RGB(250,50,50)); 
		dc.SetTextColor(m_color);
		nFont.CreateFont(m_fontHeight,m_fontWith,0,0,0,FALSE,FALSE,0,0,0,0,0,0,_TEXT("黑体"));//创建字体 
		nOldFont = dc.SelectObject(&nFont);

		UINT nFormat = 1;
		if (m_Format[i]=='0')
		{
			nFormat = DT_LEFT;
			tRect.left+=3;
		}
		else if (m_Format[i]=='1')
		{
			nFormat = DT_CENTER;
		}
		else if (m_Format[i]=='2')
		{
			nFormat = DT_RIGHT;
			tRect.right-=3;
		}
		TEXTMETRIC metric;
		dc.GetTextMetrics(&metric);
		int ofst = 0;
		ofst = tRect.Height() - metric.tmHeight;
		tRect.OffsetRect(0,ofst/2);
		dc.DrawText(m_HChar[i],&tRect,nFormat);
		dc.SelectObject(nOldFont); 
		nFont.DeleteObject(); //释放字体 
	} 
	画头部剩余部分 不绘制
	//CRect rtRect;
	//CRect clientRect;
	//GetItemRect(nItem - 1,rtRect);
	//GetClientRect(clientRect);
	//rtRect.left = rtRect.right+1;
	//rtRect.right = clientRect.right;
	//int R = m_R,G = m_G,B = m_B;
	//CRect nRect(rtRect);
	绘制立体背景 
	//for(int j = rtRect.top;j<=rtRect.bottom;j++) 
	//{ 
	//	nRect.bottom = nRect.top+1; 
	//	CBrush _brush; 
	//	_brush.CreateSolidBrush(RGB(R,G,B));//创建画刷 
	//	dc.FillRect(&nRect,&_brush); //填充背景 
	//	_brush.DeleteObject(); //释放画刷 
	//	R-=m_Gradient;G-=m_Gradient;B-=m_Gradient;
	//	if (R<0)R = 0;
	//	if (G<0)G = 0;
	//	if (B<0)B= 0;
	//	nRect.top = nRect.bottom; 
	//} 
}
LRESULT CHeaderCtrlCl::OnLayout( WPARAM wParam, LPARAM lParam )
{
	LRESULT lResult = CHeaderCtrl::DefWindowProc(HDM_LAYOUT, 0, lParam); 
	HD_LAYOUT &hdl = *( HD_LAYOUT * ) lParam; 
	RECT *prc = hdl.prc; 
	WINDOWPOS *pwpos = hdl.pwpos; 

	//表头高度为原来1.5倍,如果要动态修改表头高度的话,将1.5设成一个全局变量 
	int nHeight = (int)(pwpos->cy * m_Height);
	pwpos->cy = nHeight; 
	prc->top = nHeight; 
	return lResult; 
}

CListCtrlCl.h

#pragma once
#include "HeaderCtrlCl.h"
#include "ListCtrlBtn.h"
#include <vector>
using namespace std;

typedef struct BTNGROUP
{
	CListCtrlBtn*m_Btn[2];
	BTNGROUP()
	{
		m_Btn[0] = NULL;
		m_Btn[1] = NULL;
	
	}
}m_BtnGroup;

class CListCtrlCl : public CListCtrl
{
	DECLARE_DYNAMIC(CListCtrlCl)

public:
	CHeaderCtrlCl m_Header;
	CListCtrlCl();
	virtual ~CListCtrlCl();

protected:
	DECLARE_MESSAGE_MAP()
	virtual void PreSubclassWindow();
public:
	virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
public:
	afx_msg void OnMeasureItem(int nIDCtl, LPMEASUREITEMSTRUCT lpMeasureItemStruct);
	void MeasureItem(LPMEASUREITEMSTRUCT lpMeasureItemStruct);
public:
	// 行高
	int m_nRowHeight;
	int InsertColumn(int nCol, LPCTSTR lpszColumnHeading,
		int nFormat = LVCFMT_LEFT, int nWidth = -1, int nSubItem = -1,bool nCreatBtn = false);//是否创建按钮
public:
	// Gradient - 渐变系数,立体背景用,不用渐变设为0
	void SetHeaderBKColor(int R, int G, int B, int Gradient);
public:
	// 设置表头高度
	void SetHeaderHeight(float Height);
	CPtrList m_ptrListCol;  //保存列颜色
	CPtrList m_ptrListItem; //保存Item颜色表
	CPtrList m_colTextColor; //保存列字体颜色
	CPtrList m_ItemTextColor; //保存单元格字体颜色
	bool FindColColor(int col ,COLORREF &color); //查找列颜色
	bool FindItemColor(int col,int row,COLORREF &color);
	bool FindColTextColor(int col,COLORREF &color); //查找列字体颜色
	bool FindItemTextColor(int col,int row,COLORREF &color);
	void SetColColor(int col,COLORREF color);  //设置列颜色
	void SetItemColor(int col,int row,COLORREF color); //设置Item颜色
	void SetColTextColor(int col,COLORREF color);   //设置列文本颜色
	void SetItemTextColor(int col,int row,COLORREF color);
	void SetRowHeigt(int nHeight); //设置行高
	void SetHeaderFontHW(int nHeight,int nWith); //设置表头字体大小
	void SetHeaderTextColor(COLORREF color);
	COLORREF m_color;
	BOOL SetTextColor(COLORREF cr);
	void SetFontHW(int nHeight,int nWith);  //设置字体的高和宽
public:
	// 字体高度
	int m_fontHeight;
public:
	// 字体宽度
	int m_fontWith;
public:
	int m_nCreatBtnCol;

public://用于按钮添加
	vector<m_BtnGroup> m_BtVect;
	void SetItemBtn(int nItem, int nSubItem, HWND hMain);
};


CListCtrlCl.cpp

// ListCtrlCl.cpp : 实现文件
//

#include "stdafx.h"
#include "ListCtrlCl.h"

struct stColor
{
	int nRow;
	int nCol;
	COLORREF rgb;
};
// CListCtrlCl

IMPLEMENT_DYNAMIC(CListCtrlCl, CListCtrl)

CListCtrlCl::CListCtrlCl()
: m_nRowHeight(0)
, m_fontHeight(12)
, m_fontWith(0)
{
	m_color = RGB(0,0,0);
}

CListCtrlCl::~CListCtrlCl()
{
	for each (auto var in m_BtVect)//内存释放清理
	{
		var.m_Btn[0]->DestroyWindow();
		delete var.m_Btn[0];
		var.m_Btn[1]->DestroyWindow();
		delete var.m_Btn[1];
	}
	m_BtVect.clear();
	vector<m_BtnGroup>().swap(m_BtVect);
}


BEGIN_MESSAGE_MAP(CListCtrlCl, CListCtrl)
	ON_WM_MEASUREITEM()
	ON_WM_MEASUREITEM_REFLECT()

END_MESSAGE_MAP()



// CListCtrlCl 消息处理程序



void CListCtrlCl::PreSubclassWindow()
{
	// TODO: 在此添加专用代码和/或调用基类
	ModifyStyle(0,LVS_OWNERDRAWFIXED);
	CListCtrl::PreSubclassWindow();
	CHeaderCtrl *pHeader = GetHeaderCtrl();
	m_Header.SubclassWindow(pHeader->GetSafeHwnd());
}

void CListCtrlCl::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
{

	// TODO:  添加您的代码以绘制指定项
	TCHAR lpBuffer[256];

	LV_ITEM lvi;
	lvi.mask = LVIF_TEXT | LVIF_PARAM ;
	lvi.iItem = lpDrawItemStruct->itemID ; 
	lvi.iSubItem = 0;
	lvi.pszText = lpBuffer ;
	lvi.cchTextMax = sizeof(lpBuffer);
	VERIFY(GetItem(&lvi));


	LV_COLUMN lvc, lvcprev ;
	::ZeroMemory(&lvc, sizeof(lvc));
	::ZeroMemory(&lvcprev, sizeof(lvcprev));
	lvc.mask = LVCF_WIDTH | LVCF_FMT;
	lvcprev.mask = LVCF_WIDTH | LVCF_FMT;

	CDC* pDC;
	pDC = CDC::FromHandle(lpDrawItemStruct->hDC);
	CRect rtClient;
	GetClientRect(&rtClient);
	

	for ( int nCol=0; GetColumn(nCol, &lvc); nCol++)
	{
		if ( nCol > 0 ) 
		{
			// Get Previous Column Width in order to move the next display item
			GetColumn(nCol-1, &lvcprev) ;
			lpDrawItemStruct->rcItem.left += lvcprev.cx ;
			lpDrawItemStruct->rcItem.right += lpDrawItemStruct->rcItem.left; 
		}

		CRect rcItem;   
		if (!GetSubItemRect(lpDrawItemStruct->itemID,nCol,LVIR_LABEL,rcItem))   
			continue;   

		::ZeroMemory(&lvi, sizeof(lvi));
		lvi.iItem = lpDrawItemStruct->itemID;
		lvi.mask = LVIF_TEXT | LVIF_PARAM;
		lvi.iSubItem = nCol;
		lvi.pszText = lpBuffer;
		lvi.cchTextMax = sizeof(lpBuffer);

		VERIFY(GetItem(&lvi));
		CRect rcTemp;
		rcTemp = rcItem;

		CRgn rgn1;
		RECT tr = { rcItem.left - 1, rcItem.top, rcItem.right, rcItem.bottom };
		rgn1.CreateRectRgnIndirect(&tr);

		/*if (nCol==0)
		{
			rcTemp.left -=2;
		}*/
		if (m_nCreatBtnCol == lvi.iSubItem)//按钮位置移动
		{
			int cx = (rcTemp.left + rcTemp.right)/2;
			int cy = rcTemp.top+5;

			m_BtVect[lvi.iItem].m_Btn[0]->MoveWindow(cx - 45, cy, 40, 20);
			m_BtVect[lvi.iItem].m_Btn[1]->MoveWindow(cx + 5, cy, 40, 20);

		}
		
		if ( lpDrawItemStruct->itemState & ODS_SELECTED )
		{
			
			COLORREF color = GetBkColor(); //获取背景颜色
			//pDC->FillSolidRect(rcTemp,color);
			//内嵌窗体颜色绘制
			CBrush brush1(color);
			pDC->FillRgn(&rgn1, &brush1);

			//内嵌窗体边框绘制
			CBrush brush2(RGB(209, 209, 209));
			pDC->FrameRgn(&rgn1, &brush2, 1, 1);

			brush1.DeleteObject();
			brush2.DeleteObject();


		/*	//内嵌窗体颜色绘制  高亮处理
			CBrush brush1(GetSysColor(COLOR_HIGHLIGHT));
			pDC->FillRgn(&rgn1, &brush1);

			//内嵌窗体边框绘制
			CBrush brush2(RGB(209, 209, 209));
			pDC->FrameRgn(&rgn1, &brush2, 1, 1);

			brush1.DeleteObject();
			brush2.DeleteObject();

			//pDC->FillSolidRect(&rcTemp, GetSysColor(COLOR_HIGHLIGHT)) ;
			pDC->SetTextColor(GetSysColor(COLOR_HIGHLIGHTTEXT));	*/
		}
		else
		{
			COLORREF color = GetBkColor(); //获取背景颜色
			//pDC->FillSolidRect(rcTemp,color);
			//内嵌窗体颜色绘制
			CBrush brush1(color);
			pDC->FillRgn(&rgn1, &brush1);

			//内嵌窗体边框绘制
			CBrush brush2(RGB(209, 209, 209));
			pDC->FrameRgn(&rgn1, &brush2, 1, 1);

			brush1.DeleteObject();
			brush2.DeleteObject();


			if (FindColColor(nCol,color))//获取单元行颜色
			{
				CBrush brush1(color);
				pDC->FillRgn(&rgn1, &brush1);

				//内嵌窗体边框绘制
				CBrush brush2(RGB(209, 209, 209));
				pDC->FrameRgn(&rgn1, &brush2, 1, 1);

				brush1.DeleteObject();
				brush2.DeleteObject();;
			}
			if (FindItemColor(nCol,lpDrawItemStruct->itemID,color))//获取单元格颜色
			{
				CBrush brush1(color);
				pDC->FillRgn(&rgn1, &brush1);

				//内嵌窗体边框绘制
				CBrush brush2(RGB(209, 209, 209));
				pDC->FrameRgn(&rgn1, &brush2, 1, 1);

				brush1.DeleteObject();
				brush2.DeleteObject();;
			}
			
			//pDC->SetTextColor(m_color);
		}

		pDC->SelectObject(GetStockObject(DEFAULT_GUI_FONT));

		UINT   uFormat    = DT_CENTER ;
		if (m_Header.m_Format[nCol]=='0')
		{
			uFormat = DT_LEFT;
		}
		else if (m_Header.m_Format[nCol]=='1')
		{
			uFormat = DT_CENTER;
		}
		else if (m_Header.m_Format[nCol]=='2')
		{
			uFormat = DT_RIGHT;
		}
		TEXTMETRIC metric;
		pDC->GetTextMetrics(&metric);
		int ofst;
		ofst = rcItem.Height() - metric.tmHeight;
		rcItem.OffsetRect(0,ofst/2);
		pDC->SetTextColor(m_color);
		COLORREF color;
		if (FindColTextColor(nCol,color))
		{
			pDC->SetTextColor(color);
		}
		if (FindItemTextColor(nCol,lpDrawItemStruct->itemID,color))
		{
			pDC->SetTextColor(color);
		}
		CFont nFont ,* nOldFont; 
		nFont.CreateFont(m_fontHeight,m_fontWith,0,0,0,FALSE,FALSE,0,0,0,0,0,0,_T("宋体"));//创建字体 
		nOldFont = pDC->SelectObject(&nFont);
		
		DrawText(lpDrawItemStruct->hDC, lpBuffer, _tcslen(lpBuffer), &rcItem, uFormat);
		pDC->SelectStockObject(SYSTEM_FONT) ;
	}


}

void CListCtrlCl::OnMeasureItem(int nIDCtl, LPMEASUREITEMSTRUCT lpMeasureItemStruct)
{
	// TODO: 在此添加消息处理程序代码和/或调用默认值

	CListCtrl::OnMeasureItem(nIDCtl, lpMeasureItemStruct);
}
void CListCtrlCl::MeasureItem(LPMEASUREITEMSTRUCT lpMeasureItemStruct)
{
	if (m_nRowHeight>0)
	{
		lpMeasureItemStruct->itemHeight = m_nRowHeight;
	}
}

//是否创建按钮
int CListCtrlCl::InsertColumn(int nCol, LPCTSTR lpszColumnHeading, int nFormat /* = LVCFMT_LEFT */, int nWidth /* = -1 */, int nSubItem /* = -1 */,bool nCreatBtn)
{
	m_Header.m_HChar.Add(lpszColumnHeading);
	if (nFormat==LVCFMT_LEFT)
	{
		m_Header.m_Format = m_Header.m_Format + L"0";
	}
	else if (nFormat==LVCFMT_CENTER)
	{
		m_Header.m_Format = m_Header.m_Format + L"1";
	}
	else if (nFormat==LVCFMT_RIGHT)
	{
		m_Header.m_Format = m_Header.m_Format + L"2";
	}
	else
	{
		m_Header.m_Format = m_Header.m_Format + L"1";
	}
	if (nCreatBtn)
	{
		m_nCreatBtnCol = nCol;//记录创建按钮的列
	}
	return CListCtrl::InsertColumn(nCol,lpszColumnHeading,nFormat,nWidth,nSubItem);
}
// Gradient - 渐变系数,立体背景用,不用渐变设为0
void CListCtrlCl::SetHeaderBKColor(int R, int G, int B, int Gradient) //设置表头背景色
{
	m_Header.m_R = R;
	m_Header.m_G = G;
	m_Header.m_B = B;
	m_Header.m_Gradient = Gradient;
}

// 设置表头高度
void CListCtrlCl::SetHeaderHeight(float Height) //设置表头高度
{
	m_Header.m_Height = Height;
}
bool CListCtrlCl::FindColColor(int col,COLORREF &color) //查找列颜色
{
	int flag = 0;
	for (POSITION pos = m_ptrListCol.GetHeadPosition();pos!=NULL;)
	{
		stColor *pColor = (stColor*)m_ptrListCol.GetNext(pos);
		if (pColor->nCol==col)
		{
			flag = 1;
			color = pColor->rgb;
			break;
		}
	}
	if (1==flag)
	{
		return true;
	}
	return false;
}
bool CListCtrlCl::FindItemColor(int col,int row,COLORREF &color) //查找颜色
{
	int flag = 0;
	for (POSITION pos = m_ptrListItem.GetHeadPosition();pos!=NULL;)
	{
		stColor *pColor = (stColor*)m_ptrListItem.GetNext(pos);
		if (pColor->nCol==col&&pColor->nRow==row)
		{
			flag = 1;
			color = pColor->rgb;
			break;
		}
	}
	if (1==flag)
	{
		return true;
	}
	return false;
}
void CListCtrlCl::SetColColor(int col,COLORREF color) //设置列颜色
{
	stColor *pColor  = new stColor;
	pColor->nCol = col;
	pColor->rgb = color;
	m_ptrListCol.AddTail(pColor);
}
void CListCtrlCl::SetItemColor(int col,int row,COLORREF color) //设置格子颜色
{
	stColor *pColor  = new stColor;
	pColor->nCol = col;
	pColor->nRow = row;
	pColor->rgb = color;
	m_ptrListItem.AddTail(pColor);
}
void CListCtrlCl::SetRowHeigt(int nHeight) //高置行高
{
	m_nRowHeight = nHeight;

	CRect rcWin;
	GetWindowRect(&rcWin);
	WINDOWPOS wp;
	wp.hwnd = m_hWnd;
	wp.cx = rcWin.Width();
	wp.cy = rcWin.Height();
	wp.flags = SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOOWNERZORDER | SWP_NOZORDER;
	SendMessage(WM_WINDOWPOSCHANGED, 0, (LPARAM)&wp);
}
void CListCtrlCl::SetHeaderFontHW(int nHeight,int nWith) //设置头部字体宽和高
{
	m_Header.m_fontHeight = nHeight;
	m_Header.m_fontWith = nWith;
}
void CListCtrlCl::SetHeaderTextColor(COLORREF color) //设置头部字体颜色
{
	m_Header.m_color = color;
}
BOOL CListCtrlCl::SetTextColor(COLORREF cr)  //设置字体颜色
{
	m_color = cr;
	return TRUE;
}
void CListCtrlCl::SetFontHW(int nHeight,int nWith) //设置字体高和宽
{
	m_fontHeight = nHeight;
	m_fontWith = nWith;
}
void CListCtrlCl::SetColTextColor(int col,COLORREF color)
{
	stColor *pColor = new stColor;
	pColor->nCol = col;
	pColor->rgb = color;
	m_colTextColor.AddTail(pColor);
}
bool CListCtrlCl::FindColTextColor(int col,COLORREF &color)
{
	int flag = 0;
	for (POSITION pos = m_colTextColor.GetHeadPosition();pos!=NULL;)
	{
		stColor *pColor = (stColor*)m_colTextColor.GetNext(pos);
		if (pColor->nCol==col)
		{
			flag = 1;
			color = pColor->rgb;
			break;
		}
	}
	if (1==flag)
	{
		return true;
	}
	return false;
}
bool CListCtrlCl::FindItemTextColor(int col,int row,COLORREF &color)
{
	int flag = 0;
	for (POSITION pos = m_ItemTextColor.GetHeadPosition();pos!=NULL;)
	{
		stColor *pColor = (stColor*)m_ItemTextColor.GetNext(pos);
		if (pColor->nCol==col&&pColor->nRow==row)
		{
			flag = 1;
			color = pColor->rgb;
			break;
		}
	}
	if (1==flag)
	{
		return true;
	}
	return false;
}
void CListCtrlCl::SetItemTextColor(int col,int row,COLORREF color)
{
	stColor *pColor = new stColor;
	pColor->nCol = col;
	pColor->nRow = row;
	pColor->rgb = color;
	m_ItemTextColor.AddTail(pColor);
}

static int m_StaticBtId = 0;
void CListCtrlCl::SetItemBtn(int nItem, int nSubItem, HWND hMain)
{
	CRect rect;
	GetSubItemRect(nItem, nSubItem, LVIR_BOUNDS, rect);
	DWORD dwStyle = WS_CHILD | WS_VISIBLE | BS_OWNERDRAW;
	m_BtnGroup m_Group;
	m_Group.m_Btn[0] = new CListCtrlBtn(0,nItem, nSubItem, rect, hMain);
	m_Group.m_Btn[0]->Create(_T("查看"), dwStyle, rect, this, m_StaticBtId);

	m_StaticBtId++;
	m_Group.m_Btn[1] = new CListCtrlBtn(1,nItem, nSubItem, rect, hMain);
	m_Group.m_Btn[1]->Create(_T("巡检"), dwStyle, rect, this, m_StaticBtId);
	m_BtVect.push_back(m_Group);
	return;

}


/*	//获取选中行列
	DWORD dwPos = GetMessagePos();
	CPoint point(LOWORD(dwPos), HIWORD(dwPos));
	this->ScreenToClient(&point);
	LVHITTESTINFO lvinfo;
	lvinfo.pt = point;
	lvinfo.flags = LVHT_ABOVE;

	int nColSelected, nRowSelected;
	int nItem = SubItemHitTest(&lvinfo);
	if (nItem != -1)
	{
		nColSelected = lvinfo.iItem; //行 
		nRowSelected = lvinfo.iSubItem; //列
		}*/

使用:

DWORD dwStyle = m_list.GetExtendedStyle();
	//dwStyle |= LVS_EX_CHECKBOXES;// LVS_EX_FULLROWSELECT;			//选中某行使整行高亮(只适用与report风格的listctrl)
	//dwStyle |= LVS_EX_GRIDLINES;				//网格线(只适用与report风格的listctrl)
	m_list.SetExtendedStyle(dwStyle);


	m_list.SetBkColor(RGB(255, 255, 255));        //设置背景色
	m_list.SetRowHeigt(30);               //设置行高度
	m_list.SetHeaderHeight(1.5);          //设置头部高度
	m_list.SetHeaderFontHW(16, 0);         //设置头部字体高度,和宽度,0表示缺省,自适应 
	m_list.SetHeaderTextColor(RGB(0, 0, 0)); //设置头部字体颜色
	m_list.SetTextColor(RGB(0, 0, 0));  //设置文本颜色

	m_list.SetHeaderBKColor(255, 255, 255, 0); //设置头部背景色
	m_list.SetFontHW(14, 0);               //设置字体高度,和宽度,0表示缺省宽度

	m_list.GetHeaderCtrl()->EnableWindow(0); //禁止表头拖动

	m_list.InsertColumn(0, _T("编号"), LVCFMT_CENTER, 80);
	m_list.InsertColumn(1, _T("设备名称"), LVCFMT_CENTER, 80);
	m_list.InsertColumn(2, _T("区域"), LVCFMT_CENTER, 80);
	m_list.InsertColumn(3, _T("上次巡检时间"), LVCFMT_CENTER, 80);
	m_list.InsertColumn(4, _T("巡检结果"), LVCFMT_CENTER,80);
	m_list.InsertColumn(5, _T("操作"), LVCFMT_CENTER, 80,-1,true);

注意设置 Owner Drow Fixed 为TRUE ,Border 为 false ,以及不要设置网格线风格,否则影响整体效果。

效果图:

MFC CListCtrl控件的重绘可以通过以下几种方法来实现。 首先,可以通过重写CListCtrl的OnPaint函数来进行重绘。在OnPaint函数中,可以使用CDC类提供的绘图函数,如DrawText、DrawImage等,来绘制表控件中的内容。同时,可以使用CListCtrl的GetItemRect函数来获取每个项的位置和大小,以便准确地绘制每个项。 其次,可以使用CListCtrl的Invalidate函数来标记控件为无效状态,然后在主窗口的OnPaint函数中进行重绘。使用Invalidate函数可以通知Windows系统,在下一次重绘窗口时调用CListCtrl的OnPaint函数,从而实现重绘。这种方法适用于需要在每个窗口的重绘中都进行重绘的情况。 另外,可以使用CListCtrl的SetRedraw函数来关闭重绘功能,然后手动进行重绘。通过调用SetRedraw(TRUE)函数来重新启用重绘功能。这种方法适用于批量修改表控件中的项的情况,可以加快重绘的速度。 最后,可以通过CListCtrl的SetItemData和GetItemData函数来定制表项的显示。通过重写CListCtrl的DrawItem函数,可以对每个项进行自定义绘制。通过SetItemData函数设置项的数据,然后在DrawItem函数中使用GetItemData函数获取数据,根据数据来绘制每个项的外观。 总结来说,MFC CListCtrl控件的重绘可以通过重写OnPaint函数、使用Invalidate函数、设置SetRedraw函数或者自定义DrawItem函数来实现。具体的方法选择需要根据实际需求和应用场景来决定。
评论 28
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值