在Windows XP中資源管理器左側顯示目錄樹結構時,當在項目中移動鼠標的時候,項目標簽 的文字的字體和顏色會產生變化,使目錄的選擇非常醒目.本人在學習制作Windows98的資源管 理器的過程中,加入了相似的功能,其基本思路是:在與TreeCtrl控件關聯的類(CDirTreeCtrl) 中重載鼠標移動消息函數,設置相關的文本的顏色參數,在WM_PAINT消息映射函數定義的設備 環境中改變邏輯字體屬性(由LOGFONT結構描述)並使用設置的字體,達到項目字體變動的目的. 具體內容如下:
1>.在CDirTreeCtrl的頭文件中定義以下變 量:
HTREEITEM hItem_bc; //存放檢測項目的句柄
COLORREF ItemText_OldColor; //存放系統初始字體顏色參數,在類的初始化函數中賦值
LOGFONT logfont_old; //存放系統初始邏輯字體屬性,在類的初始化函數中賦值
struct Color_Font
{
COLORREF color;
LOGFONT logfont;
}
CMap<void*,void*,Color_Font,Color_Font&> m_mapColorFont;
2>.重載鼠標移動消息函數:
void CDirTreeCtrl::OnMouseMove(UINT nFlags, CPoint point)
{
CRect rc;
TVHITTESTINFO tvInfo;
tvInfo.pt=point;
HTREEITEM hItem=HitTest(&tvInfo); //獲得光標進入的項目的句柄
GetItemRect(hItem,&rc,TRUE);
BOOL yn=rc.PtInRect(point);
Color_Font cf;
if(yn) { //光標進入項目標簽
cf.color=RGB(0,0,150); //設置項目文本需改變的顏色參數
SetCursor(hIcon_sx); //設置手形光標,hIcon_sx為光標的句柄
hItem_bc=hItem;
}
else {
cf.color=ItemText_OldColor;
}
m_mapColorFont[hItem]=cf;
if(!m_mapColorFont.Lookup(hItem,cf))
cf.color=(COLORREF)-1;
m_mapColorFont[hItem]=cf;
Invalidate(FALSE); //強制執行OnPaint()
CTreeCtrl::OnMouseMove(nFlags, point);
}
3>.重載WM_PAINT消息函數:
void CDirTreeCtrl::OnPaint()
{
CPaintDC dc(this); // paint設備環境
CDC memDC;
memDC.CreateCompatibleDC(&dc);
CRect rcClip,rcClient;
dc.GetClipBox(&rcClip);
GetClientRect(&rcClient);
CBitmap bitmap;
bitmap.CreateCompatibleBitmap(&dc,rcClient.Width(),rcClient.Height());
memDC.SelectObject(&bitmap);
CWnd::DefWindowProc(WM_PAINT,(WPARAM)memDC.m_hDC,0);
if(hItem_bc != NULL) {
CRect rect;
UINT selflog=TVIS_DROPHILITED|TVIS_SELECTED;
Color_Font cf;
if(!(GetItemState(hItem_bc,selflog) & selflog) && m_mapColorFont.Lookup(hItem_bc,cf))
{
CFont *pFontDC;
CFont fontDC;
LOGFONT logfont;
logfont=logfont_old;
logfont.lfUnderline=TRUE; //設置字體的下劃線屬性
fontDC.CreateFontIndirect(&logfont); //創建新字體
pFontDC=memDC.SelectObject(&fontDC); //將新字體選入設備環境
memDC.SetTextColor(cf.color);
CString sItem=GetItemText(hItem_bc);
GetItemRect(hItem_bc,&rect,TRUE);
memDC.TextOut(rect.left+2,rect.top+2,sItem);
memDC.SelectObject(pFontDC);//在設備環境中恢復原字體
fontDC.DeleteObject();
}
}
dc.BitBlt(rcClip.left,rcClip.top,rcClip.Width(),rcClip.Height(),
&memDC,rcClip.left,rcClip.top,SRCCOPY);
bitmap.DeleteObject();
hItem_bc=NULL;
}