在CTreeView中给CtreeCtrl增加提示(tip)的功能(图解+源码)

CTreeView中给CtreeCtrl增加提示(tip)的功能(图解+源码)

原创作者:boqing

原文地址:

http://tb.blog.csdn.net/TrackBack.aspx?PostId=1895519

源码下载地址:

http://download.csdn.net/source/290421

 

 

 

图形界面如下:

1 新建工程

 

l        新建一个MFC工程,命名:TreeViewTipp

 

l        设置为单文档程序,注意语言选择中文(中国)

 

 

l        关键的一步:把基类设置为CTreeView

 

 

 

 

2 定义变量

TreeViewTippView.h中定义两个CString变量,用于显示提示的内容。

注意:变量类型必须是CString的,并且最好是全局变量,若在函数中定义,需要在堆上分配(new)内存。代码需要稍微改动。

 

public:

    CString m_tip1,m_tip2;

 

3 初始化变量

在构造函数中初始化,

 

CTreeViewTippView::CTreeViewTippView():m_tip1(_T("level-1")),m_tip2(_T("level-2"))

{

    // TODO: 在此处添加构造代码

}

 

说明:m_tip1用来显示一级目录的提示信息,m_tip1用来显示二级目录的提示信息。

 

4 允许弹出提示窗口

OnInitialUpdate()中添加函数EnableToolTips(TRUE);允许弹出提示窗口

 

EnableToolTips(TRUE);

 

5 改变CtreeCtrl的风格

OnInitialUpdate()改变CtreeCtrl的风格

 

    long lStyle=GetWindowLong(this->GetTreeCtrl().m_hWnd,GWL_STYLE);

    lStyle|=TVS_HASBUTTONS|TVS_HASLINES|TVS_LINESATROOT|TVS_EDITLABELS;

    SetWindowLong(this->GetTreeCtrl().m_hWnd,GWL_STYLE,lStyle);

 

6 添加节点

CtreeView添加几个节点,位置:OnInitialUpdate()

 

    HTREEITEM hroot=this->GetTreeCtrl().InsertItem(_T("根目录"),0,0);

    //一级目录信息

    HTREEITEM level1=this->GetTreeCtrl().InsertItem(_T("一级目录"),0,0,hroot);

    this->GetTreeCtrl().SetItemData(level1,(DWORD_PTR)&m_tip1);

    //二级目录信息

    HTREEITEM level2=this->GetTreeCtrl().InsertItem(_T("二级目录"),0,0,level1);

    this->GetTreeCtrl().SetItemData(level2,(DWORD_PTR)&m_tip2);

 

大家注意到了,根目录节点并没有添加提示信息,但是他能不能提示呢?是的,没有添加提示信息的节点也能显示提示功能,提示的内容是节点本身信息,当节点文本很长而又显示不完整的时候很有用处。

 

7 添加虚函数OnToolHitTest

 

//确定一个点是否位于指定工具的边界矩形之中并获

//得工具的信息

INT_PTR CTreeViewTippView::OnToolHitTest(CPoint point, TOOLINFO* pTI) const

{

       // TODO: Add your specialized code here and/or call the base class

       RECT rect;

       UINT nFlags;

       HTREEITEM hitem = this->GetTreeCtrl().HitTest( point, &nFlags );

       //判断若在某个项的文本上面

       if( hitem&&(nFlags & TVHT_ONITEMLABEL)  )

       {

              this->GetTreeCtrl().GetItemRect( hitem, &rect, TRUE );

              pTI->hwnd = m_hWnd;

              pTI->uId = (UINT_PTR)hitem;

              pTI->lpszText = LPSTR_TEXTCALLBACK;

              pTI->rect = rect;

              return pTI->uId;

       }

       return -1;

       //return CTreeView::OnToolHitTest(point, pTI);

}

 

 

8 处理TTN_NEEDTEXT通知消息

VC2005英文环境下,对CtreeViewTippView类的消息进行查找,居然没有找到TTN_NEEDTEXT,算了手动添加吧,记住:一共有三个地方需要改动:

 

第一:函数声明

 

TreeViewTippView.h中添加代码

public:

       BOOL OnToolTipText( UINT id, NMHDR * pNMHDR, LRESULT * pResult );

 

第二:消息映射

 

TreeViewTippView.cpp中找到

 

BEGIN_MESSAGE_MAP(CTreeViewTippView, CTreeView)

END_MESSAGE_MAP()

 

修改为:

 

BEGIN_MESSAGE_MAP(CTreeViewTippView, CTreeView)

       ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTW, 0, 0xFFFF, OnToolTipText)

       ON_NOTIFY_EX_RANGE(TTN_NEEDTEXTA, 0, 0xFFFF, OnToolTipText)

END_MESSAGE_MAP()

 

第三:函数实现

 

TreeViewTippView.cpp最后添加代码:

 

//在运行时改变提示

//Tooltip窗口在弹出之前,它给的父窗口发送通知消息TTN_NEEDTEXT

//请求得到要显示的文本。

BOOL CTreeViewTippView::OnToolTipText( UINT id, NMHDR * pNMHDR, LRESULT * pResult )

{

       // need to handle both ANSI and UNICODE versions of the message

       TOOLTIPTEXTA* pTTTA = (TOOLTIPTEXTA*)pNMHDR;

       TOOLTIPTEXTW* pTTTW = (TOOLTIPTEXTW*)pNMHDR;

       CString strTipText;

       UINT nID = (UINT)pNMHDR->idFrom;

       // Do not process the message from built in tooltip

       if( nID == (UINT)m_hWnd &&

              (( pNMHDR->code == TTN_NEEDTEXTA && pTTTA->uFlags & TTF_IDISHWND ) ||

              ( pNMHDR->code == TTN_NEEDTEXTW && pTTTW->uFlags & TTF_IDISHWND ) ) )

              return FALSE;

 

       // Get the mouse position

       const MSG* pMessage;

       CPoint pt;

       pMessage = GetCurrentMessage(); // get mouse pos

       ASSERT ( pMessage );

       pt = pMessage->pt;

       ScreenToClient( &pt );

 

       UINT nFlags;

       HTREEITEM hitem = this->GetTreeCtrl().HitTest( pt, &nFlags ); //Get item pointed by mouse

 

 

       strTipText.Format(_T("%s") , this->GetTreeCtrl().GetItemText( (HTREEITEM ) nID));  //get item text

       DWORD dw = (DWORD)this->GetTreeCtrl().GetItemData((HTREEITEM ) nID); //get item data

       CString* ItemData = (CString*)dw; //CAST item data

       if (ItemData!=NULL)

       {

              //CString s = ItemData; //pure virtual function

              strTipText=CString(_T(" ")) + *ItemData; //add node text to node data text

       }

#ifndef _UNICODE

       if (pNMHDR->code == TTN_NEEDTEXTA)

              lstrcpyn(pTTTA->szText, strTipText, 80);

       else

              _mbstowcsz(pTTTW->szText, strTipText, 80);

#else

       if (pNMHDR->code == TTN_NEEDTEXTA)

              _wcstombsz(pTTTA->szText, strTipText, 80);

       else

              lstrcpyn(pTTTW->szText, strTipText, 80);

#endif

       *pResult = 0;

 

       return TRUE;    // message was handled

}

 

说明:稍加修改也适合CTreeCtrl控件,当然也适合CListCtrl和CListBox控件

别忘了给顶一下

 

 

 

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值