www.pudn.com > NetTreeCtrl.zip > NetTreeCtrl.cpp


///////////////////////////////////////////////////////////////////////////// 
 
#include "stdafx.h" 
#include "Demo.h" 
#include "NetTreeCtrl.h" 
 
#ifdef _DEBUG 
#define new DEBUG_NEW 
#undef THIS_FILE 
static char THIS_FILE[] = __FILE__; 
#endif 
 
#pragma comment(lib, "mpr.lib") 
 
///////////////////////////////////////////////////////////////////////////// 
// CNetworkTreeCtrl 
 
CNetworkTreeCtrl::CNetworkTreeCtrl() 
{ 
	m_pNrRoot = NULL; 
} 
 
CNetworkTreeCtrl::~CNetworkTreeCtrl() 
{ 
	if (m_pNrRoot != NULL) 
		delete m_pNrRoot; 
} 
 
 
BEGIN_MESSAGE_MAP(CNetworkTreeCtrl, CWaitingTreeCtrl) 
	//{{AFX_MSG_MAP(CNetworkTreeCtrl) 
	ON_NOTIFY_REFLECT(TVN_DELETEITEM, OnDeleteItem) 
	//}}AFX_MSG_MAP 
END_MESSAGE_MAP() 
 
///////////////////////////////////////////////////////////////////////////// 
// CNetworkTreeCtrl message handlers 
 
 
BOOL CNetworkTreeCtrl::RefreshNetworkRoot(LPNETRESOURCE pRoot, DWORD dwStopAtDisplayType) 
{ 
	// set root resource 
	m_pNrRoot = (pRoot == NULL) ? NULL : new CNetResource(*pRoot); 
 
	// set which level of container resources not to enumerate 
	m_dwStopAt = dwStopAtDisplayType; 
 
	RefreshSubItems(TVI_ROOT); 
 
	if (m_pNrRoot == NULL) 
		return TRUE; 
 
	if ((pRoot->dwUsage & RESOURCEUSAGE_CONTAINER) == 0) 
		// not a container resource, probably tree will be empty 
		return FALSE; 
 
	return TRUE; 
} 
 
BOOL CNetworkTreeCtrl::PopulateItem(HTREEITEM hParent) 
{ 
	HANDLE hEnum = NULL; 
	NETRESOURCE nrParent; 
	LPNETRESOURCE pnrParent = &nrParent; 
 
	if (hParent == TVI_ROOT) 
		// start from specified root 
		if (m_pNrRoot == NULL) 
			pnrParent = NULL; 
		else 
			nrParent = *m_pNrRoot; 
	else 
		// start from parent item's resource 
		nrParent = *(CNetResource*)GetItemData(hParent); 
 
	// open enum 
	WNetOpenEnum(RESOURCE_GLOBALNET, RESOURCETYPE_ANY, RESOURCEUSAGE_ALL, 
		pnrParent, &hEnum); 
	if (hEnum == NULL) 
		return TRUE;	// don't try anymore 
 
	// zero = "don't know how many" 
	SetPopulationCount(0, 0); 
 
	// should be enough for just 1 item 
	const int MAX_BUFFER_LEN = 1024; 
 
	DWORD count; 
	DWORD bufsize; 
	BYTE buf[MAX_BUFFER_LEN]; 
	 
	while (TRUE) 
	{ 
		count = 1; 
		bufsize = MAX_BUFFER_LEN; 
		NETRESOURCE& nr = *(NETRESOURCE*)buf; 
		// init structure to null (needed for strings) 
		ZeroMemory(&nr, sizeof(nr)); 
 
		// retrieve next resource 
		if (WNetEnumResource(hEnum, &count, &nr, &bufsize) != NO_ERROR) 
			break;	// stop for errors 
 
		CNetResource* pNetResource = new CNetResource(nr); 
		CString sText = pNetResource->GetDisplayName(); 
 
		// update items count 
		IncreasePopulation(); 
 
		// prepare to insert a new item 
		TVINSERTSTRUCT ins; 
		ZeroMemory(&ins, sizeof(ins)); 
		 
		ins.hParent = hParent; 
		ins.hInsertAfter = TVI_LAST; 
		// set index to stored data 
		ins.item.lParam = (LPARAM)pNetResource; 
		// use stored resource to display text 
		ins.item.pszText = (LPTSTR)(LPCTSTR)sText; 
		// set other item features 
		ins.item.cChildren = (nr.dwDisplayType != m_dwStopAt) && 
			(nr.dwUsage & RESOURCEUSAGE_CONTAINER) ? 1 : 0; 
		ins.item.iImage = GetResourceImage(nr); 
		ins.item.iSelectedImage = GetResourceImage(nr); 
 
		ins.item.mask = TVIF_CHILDREN | TVIF_IMAGE | TVIF_SELECTEDIMAGE 
			| TVIF_PARAM | TVIF_TEXT; 
 
		InsertItem(&ins); 
 
//		Sleep(500);	// to test wait msg and animation 
	} 
 
	// set to full 
	SetPopulationCount(1, 1); 
//	Sleep(250);	// to test wait msg and animation 
 
	// close enum 
	WNetCloseEnum(hEnum); 
 
	// sort inserted items 
	SortChildren(hParent); 
 
	// always check children 
	return TRUE; 
} 
 
int CNetworkTreeCtrl::GetResourceImage(const NETRESOURCE &nr) 
{ 
	switch (nr.dwDisplayType) 
	{ 
	case RESOURCEDISPLAYTYPE_NETWORK: 
		return 1; 
	case RESOURCEDISPLAYTYPE_DOMAIN: 
	case RESOURCEDISPLAYTYPE_GROUP: 
		return 2; 
	case RESOURCEDISPLAYTYPE_SERVER: 
		return 3; 
	case RESOURCEDISPLAYTYPE_SHARE: 
		return (nr.dwType == RESOURCETYPE_DISK) ? 4 : 
			(nr.dwType == RESOURCETYPE_PRINT) ? 5 : 6; 
	} 
 
	return 0; 
} 
 
void CNetworkTreeCtrl::PreSubclassWindow()  
{ 
	CTreeCtrl::PreSubclassWindow(); 
 
	InitializeControl(); 
} 
 
void CNetworkTreeCtrl::InitializeControl() 
{ 
	m_imgList.Create(IDB_NETWORK_IMAGE_LIST, 16, 0, RGB(255,0,255)); 
	SetImageList(&m_imgList, TVSIL_NORMAL); 
} 
 
BOOL CNetworkTreeCtrl::GetItemResource(HTREEITEM hItem, LPNETRESOURCE pNr) 
{ 
	if (GetItemData(hItem) == 0) 
		return FALSE; 
 
	*pNr = *(CNetResource*)GetItemData(hItem); 
	return TRUE; 
} 
 
void CNetworkTreeCtrl::OnDeleteItem(NMHDR* pNMHDR, LRESULT* pResult)  
{ 
	TVITEM& item = ((NM_TREEVIEW*)pNMHDR)->itemOld; 
 
	// free memory 
	if (item.lParam != 0) 
		delete ((CNetResource*)item.lParam); 
	 
	*pResult = 0; 
}