TreeViewExt.h
上传用户:kesuntpe
上传日期:2007-01-02
资源大小:29k
文件大小:4k
源码类别:

TreeView控件

开发平台:

Visual C++

  1. #if !defined(AFX_BASETREEVIEW_H__FA327061_63AC_11D2_89CB_D1CE14573F5F__INCLUDED_)
  2. #define AFX_BASETREEVIEW_H__FA327061_63AC_11D2_89CB_D1CE14573F5F__INCLUDED_
  3. #if _MSC_VER > 1000
  4. #pragma once
  5. #endif // _MSC_VER > 1000
  6. // BaseTreeView.h : header file
  7. //
  8. #include <list>
  9. using namespace std;
  10. /////////////////////////////////////////////////////////////////////////////
  11. // CTreeViewExt view
  12. #define WM_DATAAVAILABLE WM_USER+101
  13. // type T specifies any used defined structure specific to the tree data
  14. template<class T>
  15. class CTreeViewExt
  16. {
  17. protected:
  18. virtual ~CTreeViewExt() {}
  19. struct TreeData
  20. {
  21. public:
  22. unsigned short m_nImage; // Image index in case you provide image 
  23. // for tree items
  24. CString m_strText; // Text for the item
  25. T m_Data; // Data 
  26. HTREEITEM m_hHandle; // This sometimes refers to handle of 
  27. // the tree item of this object and 
  28. // otherwise to the parent
  29. public:
  30. TreeData() : m_nImage(-1),
  31. m_hHandle(NULL)
  32. {
  33. }
  34. bool operator==(const TreeData& Data)
  35. {
  36. return m_Data == Data.m_Data;
  37. }
  38. };
  39. protected:
  40. list<TreeData> m_ItemList;
  41. public:
  42. // OnInitialUpdate starts a new thread with this function
  43. static UINT InitialThreadProc(LPVOID pData)
  44. {
  45. ASSERT(pData!=NULL);
  46. CTreeViewExt* pThis = static_cast<CTreeViewExt*>(pData);
  47. ASSERT(pThis!=NULL);
  48. return pThis->ThreadProc();
  49. }
  50. // The real thread function
  51. UINT ThreadProc()
  52. {
  53. // remember to call CoInitialize() here if you are calling COM functions
  54. GetRootItems(m_ItemList);
  55. GetTreeCtrl().SendMessage(WM_DATAAVAILABLE,0,0);
  56. list<TreeData>::iterator it, itTemp, itEnd, itInner;
  57. // here we start adding entries to the list in a loop and periodically
  58. // sending message to out control to populate the data
  59. // list intially has entries only for the root items and then it grows
  60. // as GetChildItem() returns more entries
  61. itEnd = m_ItemList.end();
  62. itEnd--;
  63. for(it = m_ItemList.begin(); it!=m_ItemList.end(); )
  64. {
  65. list<TreeData> List;
  66. GetChildItems(it,List);
  67. //adjust parent
  68. for(itInner = List.begin(); itInner!=List.end(); ++itInner)
  69. itInner->m_hHandle = it->m_hHandle;
  70. // append at the end of the list
  71. m_ItemList.insert(m_ItemList.end(),List.begin(),List.end());
  72. itTemp = it;
  73. ++it;
  74. if(itTemp==itEnd)
  75. {
  76. m_ItemList.erase(itTemp);
  77. GetTreeCtrl().SendMessage(WM_DATAAVAILABLE,0,0);
  78. itEnd = m_ItemList.end();
  79. itEnd--;
  80. }
  81. else
  82. {
  83. m_ItemList.erase(itTemp);
  84. }
  85. }
  86. return 1;
  87. }
  88. virtual void GetRootItems(list<TreeData>& List) = 0;
  89. virtual void GetChildItems(list<TreeData>::iterator it, list<TreeData>& List) = 0;
  90. virtual CTreeCtrl& GetTreeCtrl() const = 0;
  91. // just populate the tree. You can modify this function as you see fit to your
  92. // application. Note that this function gets called in the main thread
  93. LONG OnDataAvailable(WPARAM wParam, LPARAM lParam)
  94. {
  95. list<TreeData>::iterator it;
  96. HTREEITEM hItem;
  97. TV_ITEM tvI;
  98. TV_INSERTSTRUCT tvIns;
  99. HTREEITEM hParent = NULL, hPrev = NULL;
  100. bool bFirst = true;
  101. for(it = m_ItemList.begin(); it!=m_ItemList.end();++it)
  102. {
  103. hParent = it->m_hHandle;
  104. if(bFirst)
  105. {
  106. hPrev = hParent;
  107. bFirst = false;
  108. }
  109. tvI.mask = TVIF_TEXT  | TVIF_IMAGE | TVIF_SELECTEDIMAGE| TVIF_CHILDREN;
  110. tvI.pszText = (LPSTR)(LPCTSTR)it->m_strText;
  111. tvI.cchTextMax = it->m_strText.GetLength();
  112. tvI.iImage = it->m_nImage;
  113. tvI.iSelectedImage = it->m_nImage;
  114. tvIns.item = tvI;
  115. tvIns.hInsertAfter = TVI_SORT;
  116. tvIns.hParent = it->m_hHandle;
  117. tvIns.item.cChildren = 1 ;
  118. hItem = GetTreeCtrl().InsertItem(&tvIns);
  119. if(hParent!=hPrev)
  120. {
  121. GetTreeCtrl().Expand(hPrev,TVE_EXPAND);
  122. hPrev = hParent;
  123. }
  124. else
  125. {
  126. //hPrev = hParent;
  127. }
  128. it->m_hHandle = hItem;
  129. }
  130. if(hPrev)
  131. GetTreeCtrl().Expand(hPrev,TVE_EXPAND);
  132. return 1;
  133. }
  134. // Attributes
  135. public:
  136. // Operations
  137. public:
  138.  void OnInitialUpdate()
  139. {
  140. AfxBeginThread(InitialThreadProc, (LPVOID)this,THREAD_PRIORITY_LOWEST);
  141. }
  142. // Implementation
  143. protected:
  144. };
  145. /////////////////////////////////////////////////////////////////////////////
  146. // CTreeViewExt
  147. //{{AFX_INSERT_LOCATION}}
  148. // Microsoft Visual C++ will insert additional declarations immediately before the previous line.
  149. #endif // !defined(AFX_BASETREEVIEW_H__FA327061_63AC_11D2_89CB_D1CE14573F5F__INCLUDED_)