调用方式:
RECT rect;
SetRect(&rect, 0,0,200,200);
m_list.Create(m_hWnd, rect, TEXT("listbox"), WS_VISIBLE | WS_CHILD | LBS_OWNERDRAWVARIABLE |LVS_REPORT | LBS_HASSTRINGS );
m_list.AddEntry( _T("Text 1:/r/nThist is brBox Class."), RGB(0,255,0), 0 );
。。。
注意:
1。这里必须设定LBS_OWNERDRAWVARIABLE 和 LBS_HASSTRINGS 。
不设定LBS_OWNERDRAWVARIABLE 则不会进入 void MeasureItem。
2。必须加反射:
BEGIN_MSG_MAP(CAboutDlg)
REFLECT_NOTIFICATIONS()
END_MSG_MAP()。
实现代码:
template< class T, class TBase = CListBox, class TWinTraits = CControlWinTraits >
class ATL_NO_VTABLE CistBoxImpl:
public CWindowImpl< T, TBase, TWinTraits >,
public COwnerDraw< T >
{
public:
DECLARE_WND_SUPERCLASS(NULL, TBase::GetWndClassName())
CistBoxImpl()
{
}
// Message map
BEGIN_MSG_MAP(CistBoxImpl)
CHAIN_MSG_MAP_ALT( COwnerDraw< T >, 1 )
DEFAULT_REFLECTION_HANDLER()
END_MSG_MAP()
// Operations
int AddEntry(LPCTSTR lpszItem, COLORREF color, int nIndex)
{
int iItem = CListBox::InsertString(nIndex, lpszItem);
CListBox::SetItemData(iItem, color);
return iItem;
}
// Owner draw methods
void MeasureItem(LPMEASUREITEMSTRUCT lpMIS)
{
int nItem = lpMIS->itemID;
CString sLabel;
RECT rcLabel;
CListBox::GetText( nItem, sLabel );
CListBox::GetItemRect(nItem, &rcLabel);
CPaintDC dc(this->m_hWnd);
int itemHeight = dc.DrawText( sLabel, -1, &rcLabel, DT_WORDBREAK | DT_CALCRECT );
lpMIS->itemHeight = itemHeight;
}
void DrawItem(LPDRAWITEMSTRUCT lpDIS)
{
if( lpDIS->itemID==-1 ) return; // If there are no list box items, skip this message.
CDCHandle dc(lpDIS->hDC);
COLORREF rColor = (COLORREF)lpDIS->itemData; // RGB in item data
CString sLabel;
CListBox::GetText(lpDIS->itemID, sLabel);
// item selected
if ((lpDIS->itemState & ODS_SELECTED) &&
(lpDIS->itemAction & (ODA_SELECT | ODA_DRAWENTIRE)))
{
// draw color box
CBrush colorBrush;
colorBrush.CreateSolidBrush(rColor);
RECT colorRect = lpDIS->rcItem;
// draw label background
RECT labelRect = lpDIS->rcItem;
dc.FillSolidRect(&labelRect, ::GetSysColor(COLOR_HIGHLIGHT));
// draw label text
COLORREF colorTextSave;
COLORREF colorBkSave;
colorTextSave = dc.SetTextColor(::GetSysColor(COLOR_HIGHLIGHTTEXT));
colorBkSave = dc.SetBkColor(::GetSysColor(COLOR_HIGHLIGHT));
dc.DrawText( sLabel, -1, &lpDIS->rcItem, DT_WORDBREAK );
dc.SetTextColor(colorTextSave);
dc.SetBkColor(colorBkSave);
}
// item brought into box
if (lpDIS->itemAction & ODA_DRAWENTIRE)
{
RECT rect = lpDIS->rcItem;
dc.SetBkColor(rColor);
dc.FillSolidRect(&rect, rColor);
dc.DrawText( sLabel, -1, &lpDIS->rcItem, DT_WORDBREAK );
return;
}
// item deselected
if (!(lpDIS->itemState & ODS_SELECTED) &&
(lpDIS->itemAction & ODA_SELECT))
{
RECT rect = lpDIS->rcItem;
dc.SetBkColor(rColor);
dc.FillSolidRect(&rect, rColor);
dc.DrawText( sLabel, -1, &lpDIS->rcItem, DT_WORDBREAK );
return;
}
}
};
class CListBoxCtrl : public CistBoxImpl<CListBoxCtrl>
{
public:
DECLARE_WND_SUPERCLASS(_T("WTL_ListBox"), GetWndClassName())
};