📄 treelistheaderctrl.cpp
字号:
int iCol = arShows[iShow];
CTreeListColumnInfo* pColumnInfo;
pColumnInfo = (CTreeListColumnInfo*)arColumns[iCol];
nPos = nPos + pColumnInfo->m_nWidth;
if( iCol == nCol )
break;
}
}
nPos = nPos - nWinPos;
CPoint pt;
pt.x = nPos;
pt.y = 0;
ClientToScreen( &pt );
m_pDropWnd->Show( pt );
}
else
{
if( m_pDropWnd != NULL )
{
m_pDropWnd->Hide();
}
}
return TRUE;
/*
m_pDropWnd = new CTLHDropWnd;
m_pDropWnd->Create( this );
m_pDropWnd->Show();
*/
}
BOOL CTreeListHeaderCtrl::EndSizing()
{
// end sizing
CPoint point;
GetCursorPos( &point );
ScreenToClient( &point );
return EndSizing( point );
}
BOOL CTreeListHeaderCtrl::EndDraging()
{
// end draging
CPoint point;
GetCursorPos( &point );
ScreenToClient( &point );
return EndDraging( point );
}
BOOL CTreeListHeaderCtrl::HitTestSize( CPoint pt, int* pFlag, int* pCol )
{
// hit test for sizing
ASSERT( pFlag != NULL );
ASSERT( pCol != NULL );
CPtrArray& arColumns = m_pTreeListCtrl->m_arColumns;
CArray<int, int>& arShows = m_pTreeListCtrl->m_arShows;
int nWinPos = m_pTreeListCtrl->GetScrollPos( SB_HORZ );
*pFlag = 0;
*pCol = 0;
CRect rcClient;
rcClient.SetRect( 0, 0, GetHeaderWidth(), GetHeaderHeight() );
rcClient.right += 2; // fix right border for resize
rcClient.OffsetRect( -nWinPos, 0 );
// check if in client rect
if( !rcClient.PtInRect(pt) )
return FALSE;
// check if on gaps
int nPos = pt.x + nWinPos;
int nHeaderPos = 0;
int nSpaceMin = 0;
BOOL bOnSize = FALSE;
for( int iShow = 0; iShow<arShows.GetSize(); iShow++ )
{
CTreeListColumnInfo* pColumnInfo;
int iCol;
iCol = arShows[iShow];
pColumnInfo = (CTreeListColumnInfo*)arColumns[iCol];
// calculate header right border position;
nHeaderPos = nHeaderPos + pColumnInfo->m_nWidth;
// filter nosize column
if( pColumnInfo->m_dwFormat&TLF_NOSIZE )
continue;
// is close right border enough from left
if( nHeaderPos-3 <= nPos && nPos < nHeaderPos )
{
int nGap = nHeaderPos - nPos;
if( !bOnSize )
{
// find first closed right border from left
*pCol = iCol;
nSpaceMin = nGap;
bOnSize = TRUE;
}
else
{
// find more closed right border from left
if( nGap < nSpaceMin )
{
*pCol = iCol;
nSpaceMin = nGap;
}
}
}
// is close right border enough from right
if( nHeaderPos <= nPos && nPos <= nHeaderPos+2 )
{
int nGap = nPos - nHeaderPos;
if( !bOnSize )
{
// find first closed right border form right
*pCol = iCol;
nSpaceMin = nGap;
bOnSize = TRUE;
}
else
{
// find more closed right broder from right
if( nGap <= nSpaceMin )
{
*pCol = iCol;
nSpaceMin = nGap;
}
}
}
} // end for
if( bOnSize )
{
CTreeListColumnInfo* pSizeColumn = ( CTreeListColumnInfo* )arColumns[*pCol];
if( pSizeColumn->m_nWidth != 0 )
*pFlag = TLHT_ONHEADERSIZE;
else
*pFlag = TLHT_ONHEADERSPLIT;
}
return bOnSize;
}
BOOL CTreeListHeaderCtrl::HitTestGaps( CPoint pt, int* pFlag, int* pCol )
{
// hit test for show
ASSERT( pFlag != NULL );
ASSERT( pCol != NULL );
CPtrArray& arColumns = m_pTreeListCtrl->m_arColumns;
CArray<int, int>& arShows = m_pTreeListCtrl->m_arShows;
int nWinPos = m_pTreeListCtrl->GetScrollPos( SB_HORZ );
*pFlag = 0;
*pCol = 0;
CRect rcClient;
rcClient.SetRect( 0, 0, GetHeaderWidth(), GetHeaderHeight() );
rcClient.left -= 16; // fix left border for reorder
rcClient.right += 16; // fix right border for reorder
rcClient.OffsetRect( -nWinPos, 0 );
// check if in client rect
if( !rcClient.PtInRect( pt ) )
return FALSE;
// check on which column
int nPos = pt.x + nWinPos;
int nHeaderPos = 0;
int nSpaceMin = 0;
BOOL bOnGaps = FALSE;
CTreeListColumnInfo* pColumnInfo;
int iCol;
int nDelta;
// check first left border;
if( arShows.GetSize() > 0 )
{
iCol = arShows[0];
nDelta = 16;
if( nHeaderPos-nDelta <= nPos && nPos< nHeaderPos )
{
// find first closed first left border from left
ASSERT( !bOnGaps );
int nGap = nHeaderPos - nPos;
*pCol = iCol;
*pFlag = TLHT_ONHEADERLEFT;
nSpaceMin = nGap;
bOnGaps = TRUE;
}
// is close right border enough from right
CTreeListColumnInfo* pFirstColumnInfo;
pFirstColumnInfo = (CTreeListColumnInfo*)arColumns[arShows[0]];
nDelta = max( pFirstColumnInfo->m_nWidth/2, 16 );
if( nHeaderPos <= nPos && nPos <= nHeaderPos+nDelta )
{
// find first closed first left border from right
ASSERT( !bOnGaps );
int nGap = nPos - nHeaderPos;
*pCol = iCol;
*pFlag = TLHT_ONHEADERLEFT;
nSpaceMin = nGap;
bOnGaps = TRUE;
}
}
// check all right border;
for( int iShow = 0; iShow<arShows.GetSize(); iShow++ )
{
iCol = arShows[iShow];
pColumnInfo = (CTreeListColumnInfo*)arColumns[iCol];
// calculate header right border position;
nHeaderPos = nHeaderPos + pColumnInfo->m_nWidth;
// is close right border enough from left
nDelta = max(pColumnInfo->m_nWidth / 2, 16 );
if( nHeaderPos-nDelta <= nPos && nPos < nHeaderPos )
{
int nGap = nHeaderPos - nPos;
if( !bOnGaps )
{
// find first closed right border from left
*pCol = iCol;
*pFlag = TLHT_ONHEADERRIGHT;
nSpaceMin = nGap;
bOnGaps = TRUE;
}
else
{
// find more closed right border from left
if( nGap < nSpaceMin )
{
*pCol = iCol;
*pFlag = TLHT_ONHEADERRIGHT;
nSpaceMin = nGap;
}
}
}
// is close right border enough from right
if( iShow < arShows.GetUpperBound() )
{
CTreeListColumnInfo* pNextColumnInfo;
pNextColumnInfo = (CTreeListColumnInfo*)arColumns[arShows[iShow+1]];
nDelta = max( pNextColumnInfo->m_nWidth/2, 16 );
}
else
{
nDelta = 16;
}
if( nHeaderPos <= nPos && nPos <= nHeaderPos+nDelta )
{
int nGap = nPos - nHeaderPos;
if( !bOnGaps )
{
// find first closed right border from right
*pCol = iCol;
*pFlag = TLHT_ONHEADERRIGHT;
nSpaceMin = nGap;
bOnGaps = TRUE;
}
else
{
// fine more closed right border from right
if( nGap <= nSpaceMin )
{
*pCol = iCol;
*pFlag = TLHT_ONHEADERRIGHT;
nSpaceMin = nGap;
}
}
}
} // end for
return bOnGaps;
}
BOOL CTreeListHeaderCtrl::HitTest( CPoint pt, int* pFlag, int* pCol )
{
// hit test for header
ASSERT( pFlag != NULL );
ASSERT( pCol != NULL );
CPtrArray& arColumns = m_pTreeListCtrl->m_arColumns;
CArray<int, int>& arShows = m_pTreeListCtrl->m_arShows;
CTreeListColumnInfo* pColumnInfo= NULL;
int nWinPos = m_pTreeListCtrl->GetScrollPos( SB_HORZ );
*pFlag = 0;
*pCol = 0;
CRect rcClient;
rcClient.SetRect( 0, 0, GetHeaderWidth(), GetHeaderHeight() );
rcClient.OffsetRect( -nWinPos, 0 );
// check if in client rect
if( !rcClient.PtInRect(pt) )
return NULL;
// check if on header
int nPerfix = 0;
for( int iShow = 0; iShow<arShows.GetSize(); iShow++ )
{
int iCol = arShows[iShow];
pColumnInfo = (CTreeListColumnInfo*)arColumns[iCol];
CRect rcColumn;
rcColumn.SetRect( 0, 0, pColumnInfo->m_nWidth, GetHeaderHeight() );
rcColumn.OffsetRect( nPerfix, 0 );
rcColumn.OffsetRect( -nWinPos, 0 );
if( rcColumn.PtInRect( pt ) )
{
CRect rcHeader;
// if on border
rcHeader = rcColumn;
rcHeader.DeflateRect( 2, 0, 3, 0 );
if( rcHeader.Width()>0 )
{
if( !rcHeader.PtInRect( pt ) )
*pFlag |= TLHT_ONHEADERGAPS;
}
// if on sort arrow
if( pColumnInfo->m_dwFormat&TLF_CAPTION_SORT )
{
CRect rcSort;
rcSort = rcHeader;
rcSort.left = rcSort.right - TLL_WIDTH/2;
if( rcSort.PtInRect( pt ) )
*pFlag |= TLHT_ONHEADERSORT;
rcHeader.DeflateRect( 0, 0, TLL_WIDTH/2, 0 );
}
// if on image
if( rcHeader.Width()>0 && pColumnInfo->m_dwFormat&TLF_CAPTION_IMAGE )
{
CRect rcImage;
if( pColumnInfo->m_dwFormat&TLF_IMAGEALIGN_LEFT )
{
rcImage = rcHeader;
rcImage.right = rcHeader.left + TLL_WIDTH;
rcHeader.left = rcHeader.left + TLL_WIDTH;
}
else if( pColumnInfo->m_dwFormat&TLF_IMAGEALIGN_RIGHT )
{
rcImage = rcHeader;
rcImage.left = rcHeader.right - TLL_WIDTH;
rcImage.right = rcHeader.right - TLL_WIDTH;
}
else if( pColumnInfo->m_dwFormat&TLF_IMAGEALIGN_CENTER )
{
rcImage = rcHeader;
rcHeader.left = rcHeader.right;
}
else
{
rcImage = rcHeader;
rcImage.right = rcHeader.left + TLL_WIDTH;
rcHeader.left = rcHeader.left + TLL_WIDTH;
}
if( rcImage.PtInRect( pt ) )
*pFlag |= TLHT_ONHEADERIMAGE;
}
// if on text
if( rcHeader.Width()>0 && pColumnInfo->m_dwFormat&TLF_CAPTION_TEXT )
{
if( rcHeader.PtInRect( pt ) )
*pFlag |= TLHT_ONHEADERTEXT;
}
*pCol = iCol;
return TRUE;
}
nPerfix += rcColumn.Width();
}
return FALSE;
}
int CTreeListHeaderCtrl::GetSortIndex( int iCol )
{
CArray<int, int>& Sorts = m_pTreeListCtrl->m_arSorts;
int iRet = -1;
for( int iSort = 0; iSort<Sorts.GetSize(); iSort++ )
{
if( iCol == Sorts[iSort] )
{
iRet = iSort;
break;
}
}
return iRet;
}
DWORD CTreeListHeaderCtrl::GetStyle()
{
return m_dwStyle;
}
DWORD CTreeListHeaderCtrl::SetStyle( DWORD dwStyle )
{
DWORD dwoldStyle = m_dwStyle;
m_dwStyle = dwStyle;
return dwoldStyle;
}
void CTreeListHeaderCtrl::OnRButtonDown(UINT nFlags, CPoint point)
{
m_pTreeListCtrl->SetFocus();
CWnd::OnRButtonDown(nFlags, point);
}
void CTreeListHeaderCtrl::OnRButtonUp(UINT nFlags, CPoint point)
{
// TODO: Add your message handler code here and/or call default
CWnd::OnRButtonUp(nFlags, point);
}
void CTreeListHeaderCtrl::OnRButtonDblClk(UINT nFlags, CPoint point)
{
CWnd::OnRButtonDblClk(nFlags, point);
if( !m_bSizing && !m_bDraging )
{
int iFlag;
int iCol;
if( HitTestSize( point, &iFlag, &iCol ) )
{
m_pTreeListCtrl->SetColumnWidth( iCol, TLSCW_AUTOSIZE );
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -