⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 disklistctrl.cpp

📁 磁盘容量扫描、但界面和程序结构非常不错
💻 CPP
📖 第 1 页 / 共 3 页
字号:
				{
					if (m_nMouseInCode>=100)
						GetOwner()->SendMessage(WM_DISKLIST_NOTIFY, NULL, 
							(LPARAM)m_arrayFolder.GetAt(m_nMouseInCode-100));
					else
						GetOwner()->SendMessage(WM_DISKLIST_NOTIFY, NULL, 
							(LPARAM)m_arrayDrive.GetAt(m_nMouseInCode));
				}
				
				/*
				CRect rcClient, rcItem;
				GetClientRect(&rcClient);
				if (n>=0)
					GetItemRect(rcClient, rcItem, n, -1);
				else
					GetItemRect(rcClient, rcItem, -1, -n);
				CString str;
				str.Format("Item %d : %d,%d, %d, %d", m_nMouseInCode, rcItem.left, rcItem.top, rcItem.right, rcItem.bottom);
				
				MessageBox(str);*/
			}else
			{
				int nOld = m_nMouseInCode;
				m_bMouseDown = FALSE;
				m_nMouseInCode = 1000;
				m_nMouseDownCode = 1000;
				RedrawItem(nOld);
			}
		}
	}else
	{
		m_bMouseDown = FALSE;
		m_nMouseDownCode = 1000;
		RedrawItem(m_nMouseInCode);
	}
	
	CWnd::OnLButtonUp(nFlags, point);
}

int CDiskListCtrl::HitTestEx(CPoint pt)
{
	int nCount = m_arrayDrive.GetSize();

	CRect rcClient, rcItem;
	GetClientRect(&rcClient);
	int nHeight;

	if (nCount>0)
	{
		GetItemRect(rcClient, rcItem, 0, -1);
		nHeight = rcItem.Height();
		rcItem.bottom += nHeight*(nCount-1);
		if (rcItem.PtInRect(pt))
			return (pt.y - rcItem.top) / nHeight;		
	}

	//Check Folders
	nCount = m_arrayFolder.GetSize();
	if (nCount>0)
	{
		GetItemRect(rcClient, rcItem, 100, -1);
		nHeight = rcItem.Height();
		rcItem.bottom += nHeight*(nCount-1);
		if (rcItem.PtInRect(pt))
			return ((pt.y - rcItem.top) / nHeight)+100;		
	}
/*
	for (int i=0; i<nCount; i++)
	{
		GetItemRect(rcClient, rcItem, i+100, -1);
		if (rcItem.PtInRect(pt))
			return i+100;
	}
*/
	// Check Title bar
	for (int i=1; i<7; i++)
	{
		GetItemRect(rcClient, rcItem, -1, i);
		if (rcItem.PtInRect(pt))
			return -i;
	}

	return 1000;

/*	// nType -1 = titlebar
	// nType -2 = All Drivebuttons
	// nType -3 = total info button
	// nType -4 = All folderbuttons
	// nType -5 = Border rect
	// nType 0- = for button number

	CRect rcC(rcClient);
	rcC.DeflateRect(1,1,1,1);
	rc = rcC;
	int nDriveSize = GetDriveSize();

	int nHeight = GetItemHeight(rcClient);
	int nTitleHeight = GetItemHeight(rcClient, TRUE);

	switch (nType)
	{
	case -1:
		rc.top = 0;
		rc.bottom = nTitleHeight;
		rc.left -= 1;
		rc.right += 1;
		break;
	case -2:
		rc.top = nTitleHeight + 1; // Plus border
		rc.bottom = rc.top + nHeight*nDriveSize;
		break;
	case -3:
		rc.top = nTitleHeight + 1 + nHeight*nDriveSize; // Plus border
		rc.bottom = rc.top + nHeight;

		rc.left -= 1;
		rc.right += 1;
		break;
	case -4:
		rc.top = nTitleHeight + 1 + nHeight*(nDriveSize+(nDriveSize!=0)); // Plus border
		rc.bottom = rc.top + nHeight*GetFolderSize();
		break;
	case -5:
		rc.top = nTitleHeight;
		rc.bottom = rcC.bottom+1;
		rc.left -= 1;
		rc.right += 1;
		break;
	default:
		if (nType>=100) // Folders
			rc.top = nTitleHeight + 1 + nHeight*((nType-100)+(nDriveSize!=0)+nDriveSize);
		else
			rc.top = nTitleHeight + 1 + nHeight*nType;

		rc.bottom = rc.top + nHeight;		
	}
	
	
	if (nPos == -1)
		return;
	// nPos -1 = Max Width
	// nPos 0-n = for every column

	// nPos in percent
	// 4 20 11 15 15,6 15,6 18,8
	// 0 <= nCode <= 6

	// Drive item rects
	if (nType<100)
	{
		double dWidth[7] = {0.04, 0.242, 0.11, 0.156, 0.14, 0.156, 0.156};
	
		double dOff = 0;
		int nTotal = rcC.Width();
		for (int i=0; i<nPos; i++)
			dOff += nTotal*dWidth[i];
	
		rc.left += (int)dOff;
		if (nPos == 6) // Last 
			rc.right = rcC.right;
		else
			rc.right = rc.left + (int)(nTotal*dWidth[nPos]);
	}else // Folder rects
	{
		double dWidth[6] = {0.04, 0.47, 0.13, 0.13, 0.13, 0.10};
	
		double dOff = 0;
		int nTotal = rcC.Width();
		for (int i=0; i<nPos; i++)
			dOff += nTotal*dWidth[i];
	
		rc.left += (int)dOff;
		if (nPos == 5) // Last 
			rc.right = rcC.right;
		else
			rc.right = rc.left + (int)(nTotal*dWidth[nPos]);
	}*/
}
	

void CDiskListCtrl::RedrawItem(int i)
{
	if (!(i<1000))
		return;

	CRect rcClient, rcItem;
	GetClientRect(&rcClient);
	
	if (i>=0)
	{
		GetItemRect(rcClient, rcItem, i, -1);
		//rcItem.bottom +=2;
		InvalidateRect(rcItem, FALSE);
		return;
	}

	// Check Title bar
	GetItemRect(rcClient, rcItem, -1, -i);
	InvalidateRect(rcItem, FALSE);
}

void CDiskListCtrl::OnTimer(UINT nIDEvent) 
{
	if (m_nMouseInCode < 1000)
	{
		CPoint pt;
		if (!GetCursorPos(&pt))
			return;
		ScreenToClient(&pt);
		
		CRect rcClient;
		GetClientRect(&rcClient);

		if (!rcClient.PtInRect(pt))
		{
			KillTimer(5);

			int nOld = m_nMouseInCode;
			m_nMouseInCode = 1000;
			//m_bMouseDown = FALSE;
			//m_nMouseDownCode = 1000;

			RedrawItem(nOld);
		}
	}	
	CWnd::OnTimer(nIDEvent);
}

void CDiskListCtrl::SortItems(int n)
{
	int nSize = m_arrayDrive.GetSize();
	if (nSize>0)
	{
		if (m_nSortCode == n)
			m_nSortCode = -n;
		else
			m_nSortCode = n;

		qsort((void*)(m_arrayDrive.GetData()), 
				((size_t)nSize), 
				sizeof(m_arrayDrive.GetAt(0)),
				CompareItemSize);

		InvalidateRect(NULL, FALSE);
	}
}


int CDiskListCtrl::CompareItemSize(const void* f1, const void* f2)
{
	CItemInfo* pItem1 = *(CItemInfo**)f1;
	CItemInfo* pItem2 = *(CItemInfo**)f2;

	if (!pItem2->m_bAvailable && abs(m_nSortCode)!=1)
		return -1;
	else if (!pItem1->m_bAvailable && abs(m_nSortCode)!=1)
		return 1;

	switch (m_nSortCode)
	{
	case 1:
		return (long)pItem1->m_strDriveName.CompareNoCase(pItem2->m_strDriveName);		
	case 2:
		return (long)pItem1->m_strPartitionType.CompareNoCase(pItem2->m_strPartitionType);
	case 3: // Total
		return (int)(pItem1->m_ldTotalSpace/1048576 - pItem2->m_ldTotalSpace/1048576);
	case 4: //Usage
		return (long)((pItem1->GetUsage() - pItem2->GetUsage())*100);
	case 5: // Used
		return (long)((pItem1->m_ldTotalSpace - pItem1->m_ldFreeSpace - pItem2->m_ldTotalSpace
			+ pItem2->m_ldFreeSpace)/1048576);
	case 6: // Free
		return (long)((pItem1->m_ldFreeSpace - pItem2->m_ldFreeSpace)/1048576);

	case -1:
		return (long)pItem2->m_strDriveName.CompareNoCase(pItem1->m_strDriveName);		
	case -2:
		return (long)pItem2->m_strPartitionType.CompareNoCase(pItem1->m_strPartitionType);
	case -3: // Total
		return (long)(pItem2->m_ldTotalSpace/1048576 - pItem1->m_ldTotalSpace/1048576);
	case -4: //Usage
		return (long)((pItem2->GetUsage() - pItem1->GetUsage())*100);
	case -5: // Used
		return (long)((pItem2->m_ldTotalSpace - pItem2->m_ldFreeSpace - pItem1->m_ldTotalSpace
			+ pItem1->m_ldFreeSpace)/1048576);
	case -6: // Free
		return (long)((pItem2->m_ldFreeSpace - pItem1->m_ldFreeSpace)/1048576);
	}

	return 0;
}

int CDiskListCtrl::GetSize()
{
	return m_arrayDrive.GetSize() + m_arrayFolder.GetSize();
}

double CDiskListCtrl::CItemInfo::GetUsage()
{
	return (m_ldTotalSpace==0)?0:((m_ldTotalSpace-m_ldFreeSpace)/m_ldTotalSpace);
}

void CDiskListCtrl::CItemInfo::UpdateFolder(int nItemCode)
{
	if (m_pThread)
		return;

	m_nFileCount = 0;
	m_nFolderCount = 0;
	m_ldTotalSpace = 0;	// Numbers of files in folder mode

	 // Create a process to update folder info
	THREADPARAMS* pThreadParams = new THREADPARAMS;

	strcpy(pThreadParams->charPath, m_strDriveName);
	pThreadParams->nItemCode = nItemCode;

	pThreadParams->pnThreadCode = &m_nThreadCode;
	pThreadParams->pnFileCount = &m_nFileCount;
	pThreadParams->pnFolderCount = &m_nFolderCount;
	pThreadParams->pldTotalSpace = &m_ldTotalSpace;
	pThreadParams->lParam = (LPARAM)m_pCtrl;

	m_pThread = AfxBeginThread(ThreadFunc, pThreadParams, THREAD_PRIORITY_BELOW_NORMAL);
		
	//....
}

UINT CDiskListCtrl::CItemInfo::ThreadFunc(LPVOID pParam)
{
	THREADPARAMS* pThreadParams = (THREADPARAMS*)pParam;
/*
	CString strPath = pThreadParams->strPath;
	int nItemCode = pThreadParams->nItemCode;

	int* pnThreadCode = pThreadParams->pnThreadCode;
	int* pnFileCount = pThreadParams->pnFileCount;
	int* pnFolderCount = pThreadParams->pnFolderCount;
	long double* pldTotalSpace = pThreadParams->pldTotalSpace;
	CDiskListCtrl* pCtrl = (CDiskListCtrl*)pThreadParams->lParam;
*/
	((CDiskListCtrl*)pThreadParams->lParam)->OnStartUpdate(pThreadParams->nItemCode);

	UpdateDir(pThreadParams);

	((CDiskListCtrl*)pThreadParams->lParam)->PostMessage(WM_DISKLIST_UPDATE, NULL,
				LPARAM(pThreadParams->nItemCode));
	((CDiskListCtrl*)pThreadParams->lParam)->OnFinishedUpdate(pThreadParams->nItemCode);
	
	delete pThreadParams;

	return 0;
}

void CDiskListCtrl::CItemInfo::UpdateDir(THREADPARAMS* pThreadParams)
{
	HANDLE hFind;
    WIN32_FIND_DATA fd;

	char charCmp[MAX_PATH], charPath[MAX_PATH];
	strcpy(charPath, pThreadParams->charPath);
	strcpy(charCmp, charPath);
	strcat(charCmp, "*.*");	

    if ((hFind = ::FindFirstFile ((LPCTSTR) charCmp, &fd)) ==
        INVALID_HANDLE_VALUE) 
	{
        return;
    }

    do {
		if (*(pThreadParams->pnThreadCode) == -1)
			break;

		if (fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) 
		{
			strcpy(charCmp, (LPCTSTR) &fd.cFileName);

			if ((strcmp(charCmp, ".")!=0) && (strcmp(charCmp, "..")!=0)) 
			{
				(*(pThreadParams->pnFolderCount)) ++;
				strcat(pThreadParams->charPath, charCmp);
				strcat(pThreadParams->charPath, "\\");
				UpdateDir(pThreadParams);
				strcpy(pThreadParams->charPath, charPath);
            }
        }else
		{
			(*(pThreadParams->pnFileCount)) ++;
			(*(pThreadParams->pldTotalSpace)) += fd.nFileSizeLow;
		}

		if (*(pThreadParams->pnThreadCode) == -1)
			break;
		if (((*(pThreadParams->pnFileCount))+(*(pThreadParams->pnFileCount))) % 299 == 0)
		{
			((CDiskListCtrl*)pThreadParams->lParam)->PostMessage(WM_DISKLIST_UPDATE, NULL,
				LPARAM(pThreadParams->nItemCode));
		//((CDiskListCtrl*)pThreadParams->lParam)->RedrawItem(pThreadParams->nItemCode);
			Sleep(1);
		}else
			Sleep(0);
    } while (::FindNextFile (hFind, &fd));
    
	::FindClose (hFind);
}

void CDiskListCtrl::OnStopAll()
{
	int nCount = m_arrayFolder.GetSize();
	
	for (int i = 0; i < nCount; i++)
		m_arrayFolder.GetAt(i)->StopThread();
}

void CDiskListCtrl::OnPause()
{

}

void CDiskListCtrl::OnFinishedUpdate(int n)
{
	CItemInfo* pItem = m_arrayFolder.GetAt(n-100);
	pItem ->m_nThreadCode = 1;
	pItem ->m_pThread = NULL;

	m_nNrThread --;

	RedrawItem(n);
}

void CDiskListCtrl::OnStartUpdate(int n)
{
	m_nNrThread ++;
}

void CDiskListCtrl::CItemInfo::StopThread()
{
	if (m_pThread)
	{
		m_nThreadCode = -1;
		HANDLE hThread = m_pThread->m_hThread;
		::WaitForSingleObject(hThread, INFINITE);
		m_pThread = NULL;
		m_nFileCount = -1;
	}
}

inline BOOL CDiskListCtrl::CItemInfo::GetFinished()
{
	return m_nFileCount!=-1;
}

void CDiskListCtrl::UpdateAbortedFolders()
{
	int nCount = m_arrayFolder.GetSize();

	CItemInfo* pItem;
	for (int i = 0; i < nCount; i++)
	{
		pItem = m_arrayFolder.GetAt(i);
		if (!pItem->GetFinished())
			pItem->UpdateFolder(i+100);
	}
}

void CDiskListCtrl::OnItemUpdate(WPARAM wParam, LPARAM lParam)
{
	RedrawItem((int)lParam);	
}


void CDiskListCtrl::EmptyFolderArray()
{
	int nCount = m_arrayFolder.GetSize();
	
	for (int i = 0; i < nCount; i++)
		delete m_arrayFolder.GetAt(i);

	m_arrayFolder.RemoveAll();
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -