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

📄 flatheaderctrl.cpp

📁 磁盘容量扫描、但界面和程序结构非常不错
💻 CPP
📖 第 1 页 / 共 2 页
字号:
			{
				POINT point;

				point.y = rect.CenterPoint().y - ((info.rcImage.bottom-info.rcImage.top)>>1);

				if(bRight)
					point.x = rect.right - iWidth;
				else
					point.x = rect.left;

				pImageList->Draw(pDC, hditem.iImage, point, ILD_NORMAL);
			}
			else
				iWidth = 0;
		}
	}

	return iWidth;
}

INT CFlatHeaderCtrl::DrawBitmap(CDC* pDC, CRect rect, HDITEM hditem, CBitmap* pBitmap, BITMAP* pBitmapInfo, BOOL bRight)
{
	INT iWidth = 0;

	if(pBitmap)
	{
		iWidth = pBitmapInfo->bmWidth;
		if(iWidth<=rect.Width() && rect.Width()>0)
		{
			POINT point;

			point.y = rect.CenterPoint().y - (pBitmapInfo->bmHeight>>1);

			if(bRight)
				point.x = rect.right - iWidth;
			else
				point.x = rect.left;

			CDC dc;
			if(dc.CreateCompatibleDC(pDC) == TRUE) 
			{
				VERIFY(dc.SelectObject(pBitmap));
				iWidth = pDC->BitBlt(
					point.x, point.y, 
					pBitmapInfo->bmWidth, pBitmapInfo->bmHeight, 
					&dc, 
					0, 0, 
					SRCCOPY
				) ? iWidth:0;
			}
			else iWidth = 0;
		}
		else
			iWidth = 0;
	}

	return iWidth;
}

INT CFlatHeaderCtrl::DrawText(CDC* pDC, CRect rect, HDITEM hditem)
{
	CSize size;

	if(rect.Width()>0 && hditem.mask&HDI_TEXT && hditem.fmt&HDF_STRING)
	{
		size = pDC->GetTextExtent(hditem.pszText);

		switch(hditem.fmt&HDF_JUSTIFYMASK)
		{
		case HDF_LEFT:
		case HDF_LEFT|HDF_RTLREADING:
			pDC->DrawText(hditem.pszText, -1, rect, DT_LEFT|DT_END_ELLIPSIS|DT_SINGLELINE|DT_VCENTER);
			break;
		case HDF_CENTER:
		case HDF_CENTER|HDF_RTLREADING:
			pDC->DrawText(hditem.pszText, -1, rect, DT_CENTER|DT_END_ELLIPSIS|DT_SINGLELINE|DT_VCENTER);
			break;
		case HDF_RIGHT:
		case HDF_RIGHT|HDF_RTLREADING:
			pDC->DrawText(hditem.pszText, -1, rect, DT_RIGHT|DT_END_ELLIPSIS|DT_SINGLELINE|DT_VCENTER);
			break;
		}
	}

	size.cx = rect.Width()>size.cx ? size.cx:rect.Width();
	return size.cx>0 ? size.cx:0;
}

INT CFlatHeaderCtrl::DrawArrow(CDC* pDC, CRect rect, BOOL bSortAscending, BOOL bRight)
{
	INT iWidth = 0;

	if(rect.Width()>0 && m_sizeArrow.cx<=rect.Width())
	{
		iWidth = m_sizeArrow.cx;

		rect.top += (rect.Height() - m_sizeArrow.cy - 1)>>1;
		rect.bottom = rect.top + m_sizeArrow.cy - 1;

		rect.left = bRight ? rect.right-m_sizeArrow.cy:rect.left;

		// Set up pens to use for drawing the triangle
		CPen penLight(PS_SOLID, 1, m_cr3DHighLight);
		CPen penShadow(PS_SOLID, 1, m_cr3DShadow);
		CPen *pPen = pDC->SelectObject(&penLight);

		if(bSortAscending)
		{
			// Draw triangle pointing upwards
			pDC->MoveTo(rect.left + ((m_sizeArrow.cx-1)>>1) + 1,	rect.top);
			pDC->LineTo(rect.left +  (m_sizeArrow.cx-1),			rect.top + m_sizeArrow.cy - 1);
			pDC->LineTo(rect.left,									rect.top + m_sizeArrow.cy - 1);

			pDC->SelectObject(&penShadow);
			pDC->MoveTo(rect.left + ((m_sizeArrow.cx-1)>>1),	rect.top);
			pDC->LineTo(rect.left,								rect.top + m_sizeArrow.cy - 1);
		}
		else	
		{
			// Draw triangle pointing downwards
			pDC->MoveTo(rect.left + ((m_sizeArrow.cx-1)>>1)+1,	rect.top + m_sizeArrow.cy - 1);
			pDC->LineTo(rect.left +  (m_sizeArrow.cx-1),		rect.top);

			pDC->SelectObject(&penShadow);
			pDC->MoveTo(rect.left + ((m_sizeArrow.cx-1)>>1),	rect.top + m_sizeArrow.cy - 1);
			pDC->LineTo(rect.left,								rect.top);
			pDC->LineTo(rect.left + m_sizeArrow.cx,				rect.top);
		}
		
		// Restore the pen
		pDC->SelectObject(pPen);
	}

	return iWidth;
}

/////////////////////////////////////////////////////////////////////////////
// CHeaderCtrl message handlers

LRESULT CFlatHeaderCtrl::OnInsertItem(WPARAM wParam, LPARAM lParam)
{
	HDITEMEX hditemex;
	hditemex.m_iMinWidth = 0;
	hditemex.m_iMaxWidth = -1;

	ASSERT((INT)wParam <= m_arrayHdrItemEx.GetSize());
	m_arrayHdrItemEx.InsertAt(wParam, hditemex);

	return Default();
}

LRESULT CFlatHeaderCtrl::OnDeleteItem(WPARAM wParam, LPARAM lParam)
{
	ASSERT((INT)wParam < m_arrayHdrItemEx.GetSize());
	m_arrayHdrItemEx.RemoveAt(wParam);

	return Default();
}

LRESULT CFlatHeaderCtrl::OnSetHotDivider(WPARAM wParam, LPARAM lParam)
{
	if(wParam)
	{
		HDHITTESTINFO hdhti;
		hdhti.pt.x = LOWORD(lParam);
		hdhti.pt.y = HIWORD(lParam);
		ScreenToClient(&hdhti.pt);

		m_iHotDivider = SendMessage(HDM_HITTEST, 0, (LPARAM)(&hdhti));
		if(m_iHotDivider >= 0)
		{
			CRect rectItem;
			VERIFY(GetItemRect(m_iHotDivider, rectItem));
			if(hdhti.pt.x > rectItem.CenterPoint().x)
				m_iHotDivider++;
		}
	}
	else
		m_iHotDivider = (INT)lParam;

	Invalidate();

	return(LRESULT)m_iHotDivider;
}

LRESULT CFlatHeaderCtrl::OnLayout(WPARAM wParam, LPARAM lParam)
{
	LPHDLAYOUT lphdlayout = (LPHDLAYOUT)lParam;

	if(m_bStaticBorder)
		lphdlayout->prc->right += GetSystemMetrics(SM_CXBORDER)*2;

	return CHeaderCtrl::DefWindowProc(HDM_LAYOUT, 0, lParam);
}

/////////////////////////////////////////////////////////////////////////////
// CFlatHeaderCtrl message handlers

BOOL CFlatHeaderCtrl::OnEraseBkgnd(CDC* pDC) 
{
	return TRUE;
}

void CFlatHeaderCtrl::OnPaint() 
{
    CPaintDC dc(this);

    if (m_bNoFlicker)
    {
        CMemDC MemDC(&dc);
        DrawCtrl(&MemDC);
    }
    else
        DrawCtrl(&dc);
}


UINT CFlatHeaderCtrl::OnNcHitTest(CPoint point) 
{
	m_hdhtiHotItem.pt = point;
	ScreenToClient(&m_hdhtiHotItem.pt);

	m_iHotIndex = SendMessage(HDM_HITTEST, 0, (LPARAM)(&m_hdhtiHotItem));
	if(m_iHotIndex >= 0)
	{
		HDITEM hditem;
		hditem.mask = HDI_ORDER;
		VERIFY(GetItem(m_iHotIndex, &hditem));
		m_iHotOrder = hditem.iOrder;

		HDITEMEX hditemex;
		if(GetItemEx(m_iHotIndex, &hditemex))
			m_bHotItemResizable = hditemex.m_iMinWidth!=hditemex.m_iMaxWidth ? TRUE:FALSE;
	}

	return CHeaderCtrl::OnNcHitTest(point);
}


BOOL CFlatHeaderCtrl::OnSetCursor(CWnd* pWnd, UINT nHitTest, UINT message) 
{
	if(m_iHotIndex>=0 && m_hdhtiHotItem.flags&(HHT_ONDIVIDER|HHT_ONDIVOPEN) && !m_bHotItemResizable)
	{
		SetCursor(AfxGetApp()->LoadStandardCursor(IDC_ARROW));
		return TRUE;
	}

	return CHeaderCtrl::OnSetCursor(pWnd, nHitTest, message);
}

void CFlatHeaderCtrl::OnLButtonDown(UINT nFlags, CPoint point) 
{
	m_nClickFlags = nFlags;
	m_ptClickPoint = point;

	if(m_iHotIndex >= 0)
	{
		m_hditemHotItem.mask = HDI_WIDTH|HDI_FORMAT|HDI_TEXT|HDI_IMAGE|HDI_BITMAP|HDI_ORDER;
		m_hditemHotItem.pszText = m_szHotItemText;
		m_hditemHotItem.cchTextMax = sizeof(m_szHotItemText);
		VERIFY(GetItem(m_iHotIndex, &m_hditemHotItem));

		if(m_hdhtiHotItem.flags&HHT_ONHEADER)
		{
			RECT rectItem;
			VERIFY(GetItemRect(m_iHotIndex, &rectItem));
			InvalidateRect(&rectItem);
		}

		if(m_hdhtiHotItem.flags&(HHT_ONDIVIDER|HHT_ONDIVOPEN))
		{
			if(!m_bHotItemResizable)
				return;

			HDITEMEX hditemex;
			VERIFY(GetItemEx(m_iHotIndex, &hditemex));

			CRect rectItem;
			GetItemRect(m_iHotIndex, rectItem);
			ClientToScreen(rectItem);

			if(hditemex.m_iMinWidth <= hditemex.m_iMaxWidth)
			{
				CRect rectClip;
				GetClipCursor(rectClip);

				POINT point;
				GetCursorPos(&point);

				INT iOffset = point.x - rectItem.right;

				rectClip.left = rectItem.left + hditemex.m_iMinWidth + iOffset;
				rectClip.right = rectItem.left + hditemex.m_iMaxWidth + iOffset;

				ClipCursor(rectClip);
			}

			m_bResizing = TRUE;
		}
	}

	CHeaderCtrl::OnLButtonDown(nFlags, point);
}


void CFlatHeaderCtrl::OnLButtonDblClk(UINT nFlags, CPoint point) 
{
	if(m_iHotIndex>=0 && m_hdhtiHotItem.flags&(HHT_ONDIVIDER|HHT_ONDIVOPEN) && !m_bHotItemResizable)
		return;

	CHeaderCtrl::OnLButtonDblClk(nFlags, point);
}

void CFlatHeaderCtrl::OnLButtonUp(UINT nFlags, CPoint point) 
{
	m_nClickFlags = nFlags;
	m_ptClickPoint = point;

	if(m_iHotIndex >= 0)
	{
		CWnd* pWnd = GetParent();

		if(m_hdhtiHotItem.flags&(HHT_ONDIVIDER|HHT_ONDIVOPEN))
		{
			if(m_bResizing)
			{
				ClipCursor(NULL);
				m_bResizing = FALSE;
			}
		}

		if(m_hdhtiHotItem.flags&HHT_ONHEADER)
		{
			if(m_bDragging)
			{
				NMHEADER nmhdr;
				nmhdr.hdr.hwndFrom = m_hWnd;
				nmhdr.hdr.idFrom = GetDlgCtrlID();
				nmhdr.hdr.code = HDN_ENDDRAG;
				nmhdr.iItem = m_iHotIndex;
				nmhdr.iButton =	0;
				nmhdr.pitem = &m_hditemHotItem;
				if(pWnd->SendMessage(WM_NOTIFY, 0, (LPARAM)&nmhdr)==FALSE && m_iHotDivider>=0)
				{
					INT iCount = GetItemCount();
					ASSERT(m_iHotOrder < iCount);
					ASSERT(m_iHotDivider <= iCount);

					LPINT piArray = new INT[iCount*2];
					if(piArray)
					{
						GetOrderArray((LPINT)piArray, iCount);

						for(INT i=0,j=0;i<iCount;i++)
						{
							if(j == m_iHotOrder)
								j++;

							if(
								(m_iHotOrder<m_iHotDivider && i == m_iHotDivider-1) ||
								(m_iHotOrder>=m_iHotDivider && i == m_iHotDivider)
							)
								piArray[iCount+i] = piArray[m_iHotOrder];
							else
								piArray[iCount+i] = piArray[j++];
						}						

						SetOrderArray(iCount, (LPINT)&piArray[iCount]);
						delete piArray;
					}
					else
						AfxThrowMemoryException();
				}

				if(m_pDragWnd != NULL)
					delete m_pDragWnd;
				m_pDragWnd = NULL;

				if (GetCapture()->GetSafeHwnd() == GetSafeHwnd())
					ReleaseCapture();

				m_bDragging = FALSE;
				m_iHotDivider = -1;

				Invalidate();
			}
			else
			{
				RECT rectItem;
				VERIFY(GetItemRect(m_iHotIndex, &rectItem));
				InvalidateRect(&rectItem);
			}
		}
	}

	CHeaderCtrl::OnLButtonUp(nFlags, point);
}

void CFlatHeaderCtrl::OnSysColorChange() 
{
	CHeaderCtrl::OnSysColorChange();
	
	m_cr3DHighLight = ::GetSysColor(COLOR_3DHIGHLIGHT);
	m_cr3DShadow = ::GetSysColor(COLOR_3DSHADOW);
	m_cr3DFace = ::GetSysColor(COLOR_3DFACE);
	m_crText = ::GetSysColor(COLOR_BTNTEXT);
}

void CFlatHeaderCtrl::OnMouseMove(UINT nFlags, CPoint point) 
{
	if(m_nClickFlags&MK_LBUTTON && m_iHotIndex>=0)
	{
		if(m_bResizing)
			CHeaderCtrl::OnMouseMove(nFlags, point);

		if(m_hdhtiHotItem.flags&HHT_ONHEADER)
		{
			if(m_bDragging)
			{
				if(m_pDragWnd != NULL)
				{
					CRect rect;
					m_pDragWnd->GetWindowRect(&rect);

					CPoint pt = point;
					ClientToScreen(&pt);

					pt.Offset(-(rect.Width()>>1), -(rect.Height()>>1));

					m_pDragWnd->SetWindowPos(
						&wndTop, 
						pt.x, pt.y,
						0, 0, SWP_NOSIZE|SWP_SHOWWINDOW|SWP_NOACTIVATE
					);

					HDHITTESTINFO hdhti;
					hdhti.pt.x = point.x;
					hdhti.pt.y = point.y;

					INT iHotOrder = -1;
					INT iHotIndex = SendMessage(HDM_HITTEST, 0, (LPARAM)(&hdhti));
					if(iHotIndex >= 0)
					{
						HDITEM hditem;
						hditem.mask = HDI_ORDER;
						VERIFY(GetItem(iHotIndex, &hditem));
						iHotOrder = hditem.iOrder;

						CRect rectItem;
						VERIFY(GetItemRect(iHotIndex, rectItem));
						if(hdhti.pt.x > rectItem.CenterPoint().x)
							iHotOrder++;
					}

					if(iHotOrder == m_iHotOrder || iHotOrder == m_iHotOrder+1)
						iHotOrder = -1;

					if(iHotOrder != m_iHotDivider)
					{
						m_iHotDivider = iHotOrder;
						Invalidate();
					}
				}

				return;
			}
			else if(GetStyle()&HDS_DRAGDROP)
			{
				INT iDragCX = GetSystemMetrics(SM_CXDRAG);
				INT iDragCY = GetSystemMetrics(SM_CYDRAG);
				CRect rectDrag(
					m_ptClickPoint.x-iDragCX, m_ptClickPoint.y-iDragCY,
					m_ptClickPoint.x+iDragCX, m_ptClickPoint.y+iDragCY
				);

				if(!rectDrag.PtInRect(point))
				{
					NMHEADER nmhdr;
					nmhdr.hdr.hwndFrom = m_hWnd;
					nmhdr.hdr.idFrom = GetDlgCtrlID();
					nmhdr.hdr.code = HDN_BEGINDRAG;
					nmhdr.iItem = m_iHotIndex;
					nmhdr.iButton =	1;
					nmhdr.pitem = &m_hditemHotItem;

					BOOL bBeginDrag = TRUE;
					CWnd* pWnd = GetParent();
					if(pWnd != NULL)
						bBeginDrag = pWnd->SendMessage(WM_NOTIFY, 0, (LPARAM)&nmhdr)==FALSE ? TRUE:FALSE;

					if(bBeginDrag)
					{
						ASSERT(m_pDragWnd == NULL);
						m_pDragWnd = new CFHDragWnd;
						if(m_pDragWnd)
						{
							CRect rectItem;
							VERIFY(GetItemRect(m_iHotIndex, rectItem));
							ClientToScreen(&rectItem);

							m_pDragWnd->Create(rectItem, this, m_iHotIndex);
						}
					}
		
					SetCapture();
					m_bDragging = TRUE;
				}
			}
		}
	}
}

⌨️ 快捷键说明

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