CListCtrl自绘去除闪屏

/*CListCtrl控件Owner Draw Fixed属性 :true*//

 

//头文件 CMyListCtrl.h

#ifndef CMYLISTCTRL_H
#define CMYLISTCTRL_H
class CMyListCtrl
	:public CListCtrl
{
	DECLARE_DYNAMIC(CMyListCtrl)
public:
	virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
protected:
	DECLARE_MESSAGE_MAP()
	afx_msg BOOL OnEraseBkgnd(CDC* pDC);
	afx_msg void OnPaint();
private:
	BOOL DrawPicture(CDC *pDc,int nItem,int nSubItem);
	BOOL DrawText(CDC *pDc,int nItem,int nSubItem);
};
#endif


//实现文件 CMyListCtrl.cpp

#include "stdafx.h"
#include "CMyListCtrl.h"
#include <set>
IMPLEMENT_DYNAMIC(CMyListCtrl, CListCtrl)

BEGIN_MESSAGE_MAP(CMyListCtrl, CListCtrl)
	ON_WM_PAINT()
	ON_WM_ERASEBKGND()
END_MESSAGE_MAP()
BOOL CMyListCtrl::OnEraseBkgnd(CDC* pDC)
{
//响应WM_ERASEBKGND消息 
	return false;
 //屏蔽默认处理
	//return CListCtrl::OnEraseBkgnd(pDC);
}
void CMyListCtrl::DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct)
{
	// TODO: Add your code to draw the specified item
	ASSERT(lpDrawItemStruct->CtlType == ODT_LISTVIEW);
	CDC dc; 
	dc.Attach(lpDrawItemStruct->hDC);
	ASSERT(NULL != dc.GetSafeHdc());
	// Save these value to restore them when done drawing.
	COLORREF crOldTextColor = dc.GetTextColor();
	COLORREF crOldBkColor = dc.GetBkColor();

	if(lpDrawItemStruct->itemState & ODS_SELECTED)//)
	{
		dc.SetTextColor(::GetSysColor(COLOR_HIGHLIGHTTEXT));
		dc.SetBkColor(::GetSysColor(COLOR_HIGHLIGHT));
		dc.FillSolidRect(&lpDrawItemStruct->rcItem, 
		::GetSysColor(COLOR_HIGHLIGHT));
	}
	else
	{
		 dc.FillSolidRect(&lpDrawItemStruct->rcItem, crOldBkColor);
		/*if(lpDrawItemStruct->itemID%2)
		dc.FillSolidRect(&lpDrawItemStruct->rcItem, RGB(128,128,128));
		else
		dc.FillSolidRect(&lpDrawItemStruct->rcItem, RGB(255,128,255));
		*/
	}

	// If this item has the focus, draw a red frame around the
	// item's rect.
	/*if ((lpDrawItemStruct->itemAction | ODA_FOCUS) &&
	(lpDrawItemStruct->itemState & ODS_FOCUS))
	{
		CBrush br(RGB(0, 0, 128));
		dc.FrameRect(&lpDrawItemStruct->rcItem, &br);
	}*/
	CString strText(_T(""));
	CRect rcItem;
	INT nItem = lpDrawItemStruct->itemID;
	for(int i=0; i<GetHeaderCtrl()->GetItemCount(); i++)
	{
		if(i == 0)
			DrawPicture(&dc,nItem,i);
		DrawText(&dc , nItem , i);
	}

	// Reset the background color and the text color back to their
	// original values.
	dc.SetTextColor(crOldTextColor);
	dc.SetBkColor(crOldBkColor);

	dc.Detach();
}
void CMyListCtrl::OnPaint()
{
    //响应WM_PAINT消息
    CPaintDC dc(this); // device context for painting
    CRect rect;
    CRect headerRect;
    CDC MenDC;//内存ID表  
    CBitmap MemMap;
    GetClientRect(&rect);   
    GetDlgItem(0)->GetWindowRect(&headerRect);  
    MenDC.CreateCompatibleDC(&dc);  
    MemMap.CreateCompatibleBitmap(&dc,rect.Width(),rect.Height());
    MenDC.SelectObject(&MemMap);
	COLORREF crOldBkColor = dc.GetBkColor();
    MenDC.FillSolidRect(&rect,crOldBkColor);   
    //这一句是调用默认的OnPaint(),把图形画在内存DC表上  
    DefWindowProc(WM_PAINT,(WPARAM)MenDC.m_hDC,(LPARAM)0);      
    //输出  
    dc.BitBlt(0,headerRect.Height(),rect.Width(),  rect.Height(),&MenDC,0, headerRect.Height(),SRCCOPY);  
    MenDC.DeleteDC();
    MemMap.DeleteObject();
}

BOOL CMyListCtrl::DrawPicture(CDC *pDc,int nItem,int nSubItem)
{
	LVITEM vItem = {0};
	vItem.mask = LVIF_IMAGE;
	vItem.iItem = nItem;
	vItem.iSubItem = nSubItem;
	GetItem(&vItem);
	CImageList *pImageList = this->GetImageList(LVSIL_SMALL);
	CRect rcPic;
	GetSubItemRect(nItem, nSubItem, LVIR_ICON, rcPic);
	int cx, cy;
	if(pImageList != NULL){
		::ImageList_GetIconSize(*pImageList, &cx, &cy);
		pImageList->DrawIndirect(pDc, vItem.iImage, CPoint(rcPic.left , rcPic.top),
			CSize(cx, cy), CPoint(0, 0));
	}
	return TRUE;
}
BOOL CMyListCtrl::DrawText(CDC *pDc,int nItem,int nSubItem)
{
	TCHAR szString[256]=TEXT("");
	GetItemText(nItem,nSubItem,szString,256);
	CRect rcItem;
	GetSubItemRect(nItem, nSubItem, LVIR_LABEL, rcItem);
	rcItem.left += 5;
	pDc->DrawText(szString,lstrlen(szString),&rcItem,DT_VCENTER|DT_SINGLELINE|DT_END_ELLIPSIS);
	return TRUE;
}



 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值