树控件(TREECTRL)的使用
通过“FILE->NEW->PROJECTS->MFC AppWizard(EXE)”建立名为VCTREE的工程,在建立过程中选择基于对话框(Dialog based)的应用;将对话框中的默认控件删除,并将所有对话框属性中的Language域设置为Chinese(P.R.C.),以使应用程序支持中文;建立两个图标IDI_PM和IDI_CJ,用来表示图标的选中和非选中状态,对于每个图标都应建立32X32和16X16两种大小,以保证程序的需要;在对话框窗口中添加树控制对象(TREE CONTROL),并设置五个按钮“增加|删除|查看|排序|关闭”,其对应标识分别如下: 控制名称 标题名称 标识符号 树控制 IDC_TREECTRL 按钮 增 加 IDC_ADD 删 除 IDC_DEL 查 看 IDC_VIEW 排 序 IDC_SORT 关 闭 IDOK 选中树控制控件,选择“VIEW->ClassWizard->Memory Variables。 IDC_TREECTRL 引入成员变量,其变量类型为: 变量名 种类 变量类型 m_TreeCtrl Control CTreeCtrl 同时利用“MESSAGES MAP”为各命令按钮增加控制功能函数。 然后在代码文件VCTREEDlg.CPP中分别加入如下控制代码: (1)在文件开始处增加图像列表定义 CImageList Cil1,Cil2;//大小图标像列表 (2)在初始化文件开始处增加代码 BOOL CVCTREEDlg::OnInitDialog() { CDialog::OnInitDialog(); ......//原来其它代码 // TODO: Add extra initialization here // 此处开始增加代码 Cil1.Create(16,16,ILC_COLOR,2,2); Cil1.Add(AfxGetApp()->LoadIcon(IDI_PM)); Cil1.Add(AfxGetApp()->LoadIcon(IDI_CJ)); m_TreeCtrl.SetImageList(&Cil1,TVSIL_NORMAL); file://设置图象列表 DWORD dwStyles=GetWindowLong(m_TreeCtrl.m_hWnd,GWL_STYLE);//获取树控制原风格 dwStyles|=TVS_EDITLABELS|TVS_HASBUTTONS|TVS_HASLINES|TVS_LINESATROOT; SetWindowLong(m_TreeCtrl.m_hWnd,GWL_STYLE,dwStyles);//设置风格 wchar_t * CJ[4]={L"玉溪卷烟厂",L"云南卷烟厂",L"沈阳卷烟厂",L"成都卷烟厂"};//根数据名称 wchar_t * PM[4][5]={ {L"红梅一",L"红梅二",L"红梅三",L"红梅四",L"红梅五"},//产品数据项 {L"白梅一",L"白梅二",L"白梅三",L"白梅四",L"白梅五"}, {L"绿梅一",L"绿梅二",L"绿梅三",L"绿梅四",L"绿梅五"}, {L"青梅一",L"青梅二",L"青梅三",L"青梅四",L"青梅五"}}; int i,j; HTREEITEM hRoot,hCur;//树控制项目句柄 TV_INSERTSTRUCT TCItem;//插入数据项数据结构 TCItem.hParent=TVI_ROOT;//增加根项 TCItem.hInsertAfter=TVI_LAST;//在最后项之后 TCItem.item.mask=TVIF_TEXT|TVIF_PARAM|TVIF_IMAGE|TVIF_SELECTEDIMAGE;//设屏蔽 TCItem.item.pszText="数据选择"; TCItem.item.lParam=0;//序号 TCItem.item.iImage=0;//正常图标 TCItem.item.iSelectedImage=1;//选中时图标 hRoot=m_TreeCtrl.InsertItem(&TCItem);//返回根项句柄 for(i=0;i<4;i++){//增加各厂家 TCItem.hParent=hRoot; TCItem.item.pszText=CJ[i]; TCItem.item.lParam=(i+1)*10;//子项序号 hCur=m_TreeCtrl.InsertItem(&TCItem); for(j=0;j<5;j++){//增加各产品 TCItem.hParent=hCur; TCItem.item.pszText=PM[i][j]; TCItem.item.lParam=(i+1)*10+(j+1);//子项序号 m_TreeCtrl.InsertItem(&TCItem); } m_TreeCtrl.Expand(hCur,TVE_EXPAND);//展开树 } m_TreeCtrl.Expand(hRoot,TVE_EXPAND);//展开上一级树 return TRUE; // return TRUE unless you set the focus to a control } (3)增加树项功能的实现 在增加树项功能时,除了需要定义和设置插入树项的数据结构之外,还需要注意的是新增树项的名称初始时均为“新增数据”,增加后允许用户给数据项设置自定义名称。在编程时应特别注意m_TreeCtrl.EditLabel(hInsert);后面不能跟任何其它程序命令,否则这条编辑指令无效。 void CVCTREEDlg::OnAdd() { file://增加子项功能函数 HTREEITEM hSel=m_TreeCtrl.GetSelectedItem();//取得选择项句柄 if(hSel==NULL) return;//无任何选项则返回 static int nAddNo=100;//编号大于100为新增数据 TV_INSERTSTRUCT TCItem;//定义插入项数据结构 TCItem.hParent=hSel; file://设置父项句柄 TCItem.hInsertAfter=TVI_LAST;//在最后增加 TCItem.item.mask=TVIF_TEXT|TVIF_PARAM|TVIF_IMAGE|TVIF_SELECTEDIMAGE;//设屏蔽 TCItem.item.pszText="新增数据"; TCItem.item.lParam=nAddNo++;//索引号增加 TCItem.item.iImage=0;//正常图标 TCItem.item.iSelectedImage=1;//选中时图标 HTREEITEM hInsert=m_TreeCtrl.InsertItem(&TCItem);//增加 m_TreeCtrl.Expand(hSel,TVE_EXPAND); m_TreeCtrl.EditLabel(hInsert);//修改增加的数据 } (4)删除树项功能的实现 在实现删除功能时,应对存在子项的树项进行提示,以警告用户是否连同其子项一起删除。 void CVCTREEDlg::OnDel() { //删除子项功能函数 HTREEITEM hSel=m_TreeCtrl.GetSelectedItem();//取得选项句柄; if(hSel==NULL) return;//无任何选项则返回 控件的使用 if(m_TreeCtrl.ItemHasChildren(hSel))//判断是否有子项 if(MessageBox("厂家下存在品名,一同删除?","警告",MB_YESNO)==IDNO) return; m_TreeCtrl.DeleteItem(hSel); } (5)排序功能的实现 排序功能是对所选中的树项的所有子项按字符中顺序进行排序,如果想要按照其它规则进行排序,应利用SortChildrenItemBC()函数进行自行开发排序程序,这个自行开发的函数与列表控制中实现的函数基本相同,可兴趣的读可以试验。 void CVCTREEDlg::OnSort() { //排序子项功能函数 HTREEITEM hSel=m_TreeCtrl.GetSelectedItem();//取得选项句柄; if(hSel==NULL) return;//无任何选项则返回 m_TreeCtrl.SortChildren(hSel); } (6)查看功能的实现 查看功能用来查看选中树项的有关信息,函数中中显示了树项的文本名称和标识号,可以将这两个信息作为查关键字,来查看其它更详细的信息。 void CVCTREEDlg::OnView() { //查看选中项功能函数 HTREEITEM hSel=m_TreeCtrl.GetSelectedItem();//取得选项句柄; if(hSel==NULL) return;//无任何选项则返回 CString cText=m_TreeCtrl.GetItemText(hSel);//取得数据项名 LONG IDs=m_TreeCtrl.GetItemData(hSel);//取得数据项序号 char temp[100]; wsprintf(temp,"厂家:%s 编号:%05d",cText,IDs); MessageBox(temp,"选择信息"); } (7)修改功能的实现 如果不进行其它处理,当修改树项的文本名称后,就会发现其未被修改,这是因为程序中没有对修改结果进行保存处理,这就要利用TV_DISPINFO结构和SetItemText函数对TVN_ENDLABELEDIT进行处理,这样就可以正确地实现修改功能。 void CVCTREEDlg::OnEndlabeleditTree(NMHDR* pNMHDR, LRESULT* pResult) { TV_DISPINFO* pTVDispInfo = (TV_DISPINFO*)pNMHDR; // TODO: Add your control notification handler code here if(pTVDispInfo->item.pszText==0) return;//用户取消修改操作 m_TreeCtrl.SetItemText(pTVDispInfo->item.hItem, pTVDispInfo->item.pszText);//设置新数据 *pResult = 0; } |
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论