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

📄 disktreectrl.cpp

📁 磁盘容量扫描、但界面和程序结构非常不错
💻 CPP
📖 第 1 页 / 共 3 页
字号:
	if(pDC == NULL || pInfo==NULL)          
		return;
	
	TitleStr = t_title;
	DateStr = t_date;
	
	//create lc font, and Bold lc Font
	int nFontSize = -((pDC->GetDeviceCaps(LOGPIXELSY) * 10) / 72);
    CString strFontName = "Arial";
    lcFont.CreateFont(-11, 0,0,0, FW_NORMAL, 0,0,0, DEFAULT_CHARSET,
                         OUT_CHARACTER_PRECIS, CLIP_CHARACTER_PRECIS, DEFAULT_QUALITY,
                          DEFAULT_PITCH | FF_DONTCARE, strFontName);
    BoldFont.CreateFont(-13, 0,0,0, FW_BOLD, 0,0,0, DEFAULT_CHARSET,
                         OUT_CHARACTER_PRECIS, CLIP_CHARACTER_PRECIS, DEFAULT_QUALITY,
                          DEFAULT_PITCH | FF_DONTCARE, strFontName);
	
	compute_metrics(pDC);
	int nMaxPage = m_nMaxRowCount/m_nRowsPerPage + 1;//Compute this again in case user changed printer
	pInfo->SetMaxPage(nMaxPage);
	pInfo->m_nCurPage = 1;  // start printing at page# 1
	
	return;
}

//***********************ONPRINT*************************
void CTreeListPrinting::OnPrint(CDC* pDC, CPrintInfo* pInfo) 
{
	if(NULL == pDC || NULL == pInfo)           
		return;
	
	//This has to be in OnPrint() or else PrintPreview goes screwy
	pOldFont = pDC->GetCurrentFont();
	
	//Fit all columns to 1 page, regardless of column number.
	pDC->SetMapMode(MM_ANISOTROPIC);
	
	//For every 1 List Control pixel
	pDC->SetWindowExt(1, 1);
	
	//The printer has ratio more dots
	pDC->SetViewportExt(m_ratiox, m_ratioy);
	
	int nStartRow = (pInfo->m_nCurPage - 1)*m_nRowsPerPage;
	int nEndRow = nStartRow+m_nRowsPerPage;
	if(nEndRow > m_nMaxRowCount)       
		nEndRow = m_nMaxRowCount;
	
	PrintHeader(pDC, pInfo);     //print the header
	
	pDC->SetWindowOrg(-1*page_rc.left, 0);
	PrintFooter(pDC, pInfo);	  //Print the footer
	pDC->SetWindowOrg(-1*page_rc.left, -1*HEADER_HEIGHT*m_nRowHeight);
	PrintHeaderControl(pDC, pInfo);//Print the header Control, Manually
	pDC->SelectObject(&lcFont);//Use the LC normal font
	pDC->SetTextColor(RGB(0,0,0));//Black text on
	pDC->SetBkColor(RGB(255,255,255));//White paper
	
	CRect     rcBounds;
	lc->GetItemRect(nStartRow, &rcBounds, LVIR_BOUNDS);
	
	//offset top margin of rcBounds by ListControl header
	CRect     rc;
	lc->GetHeaderCtrl()->GetClientRect(&rc);
	rcBounds.OffsetRect(0, -rc.Height());
	pDC->OffsetWindowOrg(rcBounds.left, rcBounds.top);
	
	//start printing rows
	for(int i = nStartRow; i < nEndRow; i++)
		DrawRow(pDC, i);
	
	//SetWindowOrg back for next page
	pDC->SetWindowOrg(0,0);
	pDC->SelectObject(pOldFont);//Put the old font back
	
	return;
}

//Set the extents after calling this function because it uses printer extents
//He is using a list in here have to figure out what to do.
//********************************PRINT_HEADER************************************
void CTreeListPrinting::PrintHeader(CDC *pDC, CPrintInfo *pInfo)
{
	pDC->SelectObject(&BoldFont);
	pDC->SetTextColor(RGB(0,0,0));//Black text on
	pDC->SetBkColor(RGB(255,255,255));//White paper
	
	CRect rc = page_rc;
	rc.bottom = rc.top+m_nRowHeight;
	
	//print App title on top right margin
	pDC->DrawText(TitleStr, &rc,  DT_SINGLELINE | DT_NOPREFIX | DT_VCENTER | DT_RIGHT  | DT_NOCLIP);
	
	return;
}

//print footer with a line and date, and page number
//****************************PRINT_FOOTER****************************************
void CTreeListPrinting::PrintFooter(CDC *pDC, CPrintInfo *pInfo)
{
	CRect     rc = page_rc;
	rc.top = rc.bottom - FOOTER_HEIGHT*m_nRowHeight;
	rc.bottom = rc.top + m_nRowHeight;
	draw_line_at(pDC, rc.top);     //draw line
	
	//draw page number
	CString   sTemp ;
	rc.OffsetRect(0, m_nRowHeight/2);
	sTemp.Format("%d", pInfo->m_nCurPage);
	pDC->DrawText(sTemp,-1,rc, DT_LEFT | DT_SINGLELINE | DT_NOPREFIX | DT_NOCLIP | DT_VCENTER);
	
	//Now draw the DateStr at bottom of page
	pDC->DrawText(DateStr,-1,rc, DT_RIGHT | DT_SINGLELINE | DT_NOPREFIX | DT_NOCLIP | DT_VCENTER);
	
	return;
}


//Do the cleanup
//********************ONEND_PRINTING*****************
void CTreeListPrinting::OnEndPrinting(CDC* pDC, CPrintInfo* pInfo)
{
	lcFont.DeleteObject();
	BoldFont.DeleteObject();
	return;
}

//This function sets alls of the row and metric member vars
//************************COMPUTE_METRICS*********************
void CTreeListPrinting::compute_metrics(CDC *pDC)
{
	//This includes width for all columns
	CRect row_rc;	lc->GetItemRect(0, &row_rc, LVIR_BOUNDS);
	
	//Get the list control window DC
	CDC  *pCtlDC = lc->GetDC(); if(NULL == pCtlDC) return;
	
	//so we can get the avg character width
	TEXTMETRIC tm;   pCtlDC->GetTextMetrics(&tm);
	
	//Lets get the ratios for scaling to printer DC
	//Fit all columns to 1 page, regardless of column number.
	m_ratiox = pDC->GetDeviceCaps(HORZRES)/(row_rc.Width() + (LEFT_MARGIN+RIGHT_MARGIN)*tm.tmAveCharWidth);
	
	//width of pDC/whats got to fit into it in lcDC units
	m_ratioy = pDC->GetDeviceCaps(LOGPIXELSY)/pCtlDC->GetDeviceCaps(LOGPIXELSY);
	
	lc->ReleaseDC(pCtlDC);
	
	//Set up a page rc in list control units that accounts for left and right margins
	page_rc.SetRect(0,0, pDC->GetDeviceCaps(HORZRES), pDC->GetDeviceCaps(VERTRES));
	page_rc.bottom = page_rc.bottom/m_ratioy;//Convert units to List Control
	page_rc.right = page_rc.right/m_ratiox;
	page_rc.left = LEFT_MARGIN*tm.tmAveCharWidth;//adjust sides for magins
	page_rc.right -= RIGHT_MARGIN*tm.tmAveCharWidth;
	
	m_nRowHeight = row_rc.Height();//Get the height of a row.
	int pRowHeight = (int)(m_nRowHeight*m_ratioy);//Get RowHeight in printer units.
	m_nRowsPerPage = pDC->GetDeviceCaps(VERTRES)/pRowHeight;//How many rows will fit on page?
	m_nRowsPerPage -= (HEADER_HEIGHT+FOOTER_HEIGHT);//After header and footer rows
	m_nRowsPerPage -= 1; //After header Control row
	
	return;
}

//You can't just have the header control print itself. 1st of all it looks crappy.
//2nd if part of header control is off screen does not print itself.
//So we will manually print it.
//************************PRINTHEADERCONTROL****************************
void CTreeListPrinting::PrintHeaderControl(CDC *pDC, CPrintInfo *pInfo)
{
	UINT    dtFlags = DT_SINGLELINE|DT_NOPREFIX|DT_VCENTER|DT_LEFT;//drawing flags
	CHeaderCtrl* hc = lc->GetHeaderCtrl();
	hc_items = hc->GetItemCount(); 
	if (hc_items < 1) return; //Remember that hc_items is also used to draw rows.
	int order_array[30];//Shouln't have more than 30 columns
	hc->GetOrderArray(order_array, hc_items);
	
	char temp_str[1024];
	HDITEM  phi;
	phi.mask = HDI_TEXT | HDI_WIDTH ;
	phi.cchTextMax = 1024;
	phi.pszText = temp_str;
	
	CRect rc(0,0,0,m_nRowHeight);
	
	for (int i = 0; i < hc_items; i++)
	{
		hc->GetItem(order_array[i], &phi);//Get in viewed order
		rc.right += phi.cxy;
		pDC->DrawText(temp_str, -1, rc, dtFlags);
		rc.left += phi.cxy;
	}
	
	//Now draw the line below header control
	draw_line_at(pDC, rc.bottom);
	
	return;
}

//*************************************DRAWROW********************************************
void CTreeListPrinting::DrawRow(CDC *pDC, int nItem)
{
	if (hc_items < 1) //Then nothing to print
		return;  
	
	int order_array[30];//Shouln't have more than 30 columns
	lc->GetColumnOrderArray(order_array, hc_items);
	
	CString temp_str;
	LV_COLUMN lvc;
	lvc.mask = LVCF_WIDTH;
	
	CRect rc; lc->GetItemRect(nItem, rc, LVIR_BOUNDS);
	int offset = pDC->GetTextExtent(" ", 1).cx;//Returns CSIZE so get cx member of CSIZE object.
	rc.left += offset/2;//This makes it so that label will be over a little bit
	rc.right -= offset;//Just keep this stuff it DOES look better.

	CRect r(rc);

	for (int i = 0; i < hc_items; i++)
	{
		int nOffset = 0;
		if (i==0)
			nOffset = lc->DrawLine(pDC, nItem, r);
		lc->GetColumn(order_array[i], &lvc);//Get in viewed order
		temp_str = lc->GetItemText(nItem, order_array[i]);
		r.left += nOffset;
		pDC->DrawText(temp_str, -1, r, DT_SINGLELINE|DT_NOPREFIX|DT_VCENTER|DT_LEFT);
		r.left += (lvc.cx - nOffset);
	}

	pDC->MoveTo(rc.Width() - lc->GetColumnWidth(0) + offset, rc.bottom);
	pDC->LineTo(page_rc.right, rc.bottom);//Use the page_rc to figure out the width of the line
	
	
	
	return;
}

//Just pass this function a y position to draw the line at.
//*************************DRAW_LINE_AT************************************
void CTreeListPrinting::draw_line_at(CDC *pDC, unsigned int y)
{
	pDC->MoveTo(0, y);
	pDC->LineTo(page_rc.right, y);//Use the page_rc to figure out the width of the line
	
	return;
}

int CDiskTreeCtrl::DrawLine(CDC* pDC, int nItem, const CRect& rc)
{
	CRect rcBounds(rc);
	rcBounds.OffsetRect(0,rc.Height()/3);
	int nLeft = 0;
	int m_cxImage = rcBounds.Height()/2;
	int m_cyImage = rcBounds.Height();

	int nColWidth = GetColumnWidth(0);
	int nOffset = (rcBounds.Height() - m_cyImage) >> 1; 	
	
	CPen psPen(PS_SOLID, 1, RGB(192,192,192));
    CPen* pOldPen = pDC->SelectObject(&psPen);

	CTreeItem *pSelItem = reinterpret_cast<CTreeItem*>(GetItemData(nItem));
	CTreeItem* pRoot = GetRootItem();
	int iIndent = GetIndent(pSelItem);
	//setup plus/minus rectangle
	int nHalfImage = (m_cxImage >> 1);	
	int yDown = rcBounds.top;
	int nBottomDown = yDown + nHalfImage+nOffset;
	
	SIZE right_bottom = {(m_cxImage>>1)+2+1, (m_cyImage>>1)+2+1};//from ANDY : the '+ 1' is to center the [+] or [-] 
	int left = rcBounds.left  + GetIndent(pSelItem) * m_cxImage - nHalfImage;
	
	int top = nBottomDown - (right_bottom.cy >> 1);
	POINT left_top = {left -  (right_bottom.cx >> 1), top};
	
	BOOL bChild = ItemHasChildren(pSelItem);
	BOOL bCollapsed = IsCollapsed(pSelItem);
	//draw outline	
	
	while(pRoot != pSelItem)
	{
		CTreeItem* pParent = GetParentItem(pSelItem);
		POSITION pos = pParent->m_listChild.GetTailPosition();
		while(pos!=NULL)
		{
			CTreeItem *pLastChild = (CTreeItem*)pParent->m_listChild.GetPrev(pos);
			int nIndex = GetCurIndex(pLastChild);
			//no drawing outside the 1st columns right
			int xLine =  rcBounds.left + GetIndent(pLastChild) * m_cxImage - nHalfImage;
			if(nIndex == nItem && (GetIndent(pLastChild)==iIndent))
			{
				//draw '-
				int x;
				pDC->MoveTo(xLine, yDown);
				pDC->LineTo(xLine, nBottomDown);
				// -
				xLine + nHalfImage > nColWidth ? x = nColWidth: x = xLine + nHalfImage;
				
				pDC->MoveTo(xLine, nBottomDown);
				pDC->LineTo(x, nBottomDown);

				nLeft += nHalfImage;
				break;
			}
			else
			if(nIndex > nItem && (GetIndent(pLastChild)==iIndent))
			{
				//draw |-
				int x;
				xLine + nHalfImage > nColWidth ? x = nColWidth : x = xLine + nHalfImage;
				pDC->MoveTo(xLine, nBottomDown);
				pDC->LineTo(x, nBottomDown);
				//-
				pDC->MoveTo(xLine, yDown);
				pDC->LineTo(xLine, rcBounds.bottom);

				nLeft += nHalfImage;
				break;
			}
			else
			if(nIndex > nItem && (GetIndent(pLastChild) < iIndent))
			{
				//draw |
				pDC->MoveTo(xLine, yDown);
				pDC->LineTo(xLine, rcBounds.bottom);

				nLeft += nHalfImage;
				break;
			}else
				nLeft += nHalfImage;

		}			
		pSelItem = pParent;//next
	}
	//draw plus/minus sign
	if(bChild)
	{
		//erase bkgrnd
		CRect rcBounds(left_top, right_bottom);
		pDC->FillRect(rcBounds, &CBrush(RGB(255,255,255)));
		//draw rectangle	
		pDC->Rectangle(rcBounds);
		//draw plus/minus sign
		int topdown = nBottomDown;
		if(bCollapsed)
		{
			//plus
			pDC->MoveTo(left, topdown-2);
			pDC->LineTo(left, topdown+3);
			//	
			pDC->MoveTo(left-2, topdown);
			pDC->LineTo(left+3, topdown);
		}
		else {
			//minus 
			pDC->MoveTo(left-2, topdown);
			pDC->LineTo(left+3, topdown);
			int nOffset = (rcBounds.Height() - m_cyImage)/2;
			pDC->MoveTo(left+ m_cxImage, rcBounds.top + m_cyImage+(nOffset/2));
			pDC->LineTo(left + m_cxImage, rcBounds.bottom);
		}
	}
	pDC->SelectObject(pOldPen);
	
	return iIndent*nHalfImage*2+nHalfImage;
	/*int nOffset=0;
	int nOffsetWidth = 8;

	CTreeItem* pRoot = GetRootItem();

	CTreeItem *pParent = reinterpret_cast<CTreeItem*>(GetItemData(nItem));
	CTreeItem *pItem = pParent;

	CItemInfo* lp = GetData(pItem);
	
	int iIndent = GetIndent(pItem);
	int nListItem = GetCurIndex(pItem);
	CTreeItem *pSelItem = pItem;
	while(pRoot != pSelItem)
	{
		CTreeItem* pParent = GetParentItem(pSelItem);
		POSITION pos = pParent->m_listChild.GetTailPosition();
		while(pos!=NULL)
		{
			CTreeItem *pLastChild = (CTreeItem*)pParent->m_listChild.GetPrev(pos);
			int nIndex = GetCurIndex(pLastChild);
			//no drawing outside the 1st columns right
			if (nIndex == nListItem && (GetIndent(pLastChild)==iIndent))
			{
				pDC->MoveTo(rc.left + nOffset, (rc.bottom-rc.top)/2 + rc.top);
				pDC->LineTo(rc.left + nOffset + nOffsetWidth, (rc.bottom-rc.top)/2 + rc.top);

				nOffset += nOffsetWidth;
				
				break;
			}
			else if(nIndex > nListItem && (GetIndent(pLastChild)==iIndent))
			{
				//draw |-
				pDC->MoveTo(rc.left + nOffset, rc.top);
				pDC->LineTo(rc.left + nOffset, rc.bottom);
				
				pDC->MoveTo(rc.left + nOffset, (rc.bottom-rc.top)/2 + rc.top);
				pDC->LineTo(rc.left + nOffset + nOffsetWidth, (rc.bottom-rc.top)/2 + rc.top);

				nOffset += nOffsetWidth;

				
				break;
			}
			else if(nIndex > nListItem && (GetIndent(pLastChild) < iIndent))
			{
				//draw |
				pDC->MoveTo(rc.left + nOffset, rc.top);
				pDC->LineTo(rc.left + nOffset, rc.bottom);

				nOffset += nOffsetWidth;
				
				break;
			}else
			{
				nOffset += nOffsetWidth;
				break;
			}
		}			
		pSelItem = pParent;//next
	}
	
	return nOffset;*/
}

⌨️ 快捷键说明

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