在MFC应用程序中,标准公共控件并不支持树形控件的多选功能。这就需要开发者自行实现。感谢Richard Hazlewood的文章,他提供了一个简单的实现方式,但仅限于简单的橡皮筋选择。本文将介绍如何实现一个类似于资源管理器的带有透明选择矩形的树形控件。
Eugen Podsypalnikov的CCoverWnd类给提供了一个实现透明选择矩形的思路,但焦点问题和CWnd派生实现让思考,或许让树形控件自身实现选择绘制会更好。因此,有了CMultiSelTriCheckTreeCtrl类。
CMultiSelTriCheckTreeCtrl是一个MFC包装类,封装了多选树形控件的功能。它派生自CTriCheckStateTreeCtrl类,后者实现了三态复选框的树形控件。
CMultiSelTriCheckTreeCtrl的接口与Richard Hazlewood的CMultiTree非常相似,因为本质上只是更改了选择绘制代码。以下是公共接口:
class CMultiSelTriCheckTreeCtrl : public CTriCheckStateTreeCtrl
{
public:
inline BOOL IsMultiSelectable() const;
void SetMultiSelectable(BOOL bMultiSel = TRUE);
inline BOOL IsSelected(HTREEITEM hItem) const;
size_t GetSelectedCount() const;
HTREEITEM GetFirstSelectedItem() const;
HTREEITEM GetNextSelectedItem(HTREEITEM hItem) const;
HTREEITEM GetPrevSelectedItem(HTREEITEM hItem) const;
void SelectAll(BOOL bSelect = TRUE);
void SelectRange(HTREEITEM hFirst, HTREEITEM hLast, BOOL bOnly = TRUE);
BOOL SetItemState(HTREEITEM hItem, UINT nState, UINT nStateMask);
UINT GetItemState(HTREEITEM hItem, UINT nStateMask) const;
virtual void ToggleCheckSelectedItem();
virtual void DeleteSelectedItem();
void GetSelectedList(TreeItemList& selectedList) const;
};
以下是如何在对话框应用程序中使用CMultiSelTriCheckTreeCtrl类的基本步骤:
创建一个名为CMultiSelTreeDemo的基于对话框的MFC项目。
将以下源文件(位于code_base文件夹下)添加到工作空间中:
打开预编译头文件,通常是StdAfx.h,添加以下代码行:
#include "..\code_base\CustomDrawCommon.h"
如果使用的是Visual Studio 6.0,还需要在StdAfx.h的开头添加以下代码:
#pragma warning(disable: 4786) // 禁用VC6中烦人的警告
#ifndef WINVER
#define WINVER 0x0501
#endif // WINVER
#ifndef _WIN32_WINNT
#define _WIN32_WINNT 0x0501
#endif // _WIN32_WINNT
使用资源编辑器打开对话框,从控件工具栏拖放一个树形控件到对话框上。
为该树形控件添加一个相应的控件成员变量,命名为m_myTreeCtrl,IDE将为添加必要的代码,看起来像这样:
CTreeCtrl m_myTreeCtrl;
打开对话框类的头文件,在文件开头添加#include指令,如下所示:
#include "..\code_base\CustomDrawControl.h"
将m_myTreeCtrl的类型从CTreeCtrl更改为CMultiSelTriCheckTreeCtrl。