📄 multilistbox.cpp
字号:
// MultiListBox.cpp : implementation file
//
#include "stdafx.h"
#include "MultiListBox.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#define MIN_TAB_SIZE 1
CString CMultiListBox::m_strCharSet="0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ abcdefghijklmnopqrst啊";
////////////////////////////////
// CMultiListBox
////////////////////////////////
CMultiListBox::CMultiListBox()
{
m_nAvgCharWidth=8;
m_nSpacing=2;
m_aTabs.SetSize(MIN_TAB_SIZE);
m_aColWidth.SetSize(MIN_TAB_SIZE);
m_nTabs=MIN_TAB_SIZE;
InitColWidth();
}
CMultiListBox::~CMultiListBox()
{
}
////////////////////////////////////////////
//
////////////////////////////////////////////
BEGIN_MESSAGE_MAP(CMultiListBox, CListBox)
//{{AFX_MSG_MAP(CMultiListBox)
ON_MESSAGE(LB_ADDSTRING, OnAddString)
ON_MESSAGE(LB_INSERTSTRING, OnInsertString)
ON_MESSAGE(LB_DELETESTRING, OnDeleteString)
ON_MESSAGE(LB_RESETCONTENT, OnResetContent)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
////////////////////////////////////////////
//
////////////////////////////////////////////
void CMultiListBox::SetColumnSpace(int nSpacing)
{
if(nSpacing!=m_nSpacing)
{
m_nSpacing=nSpacing;
CalculateTabs();
SetTabStops(m_nTabs,(LPINT)&m_aTabs[0]);
}
}
////////////////////////////////////////////
//
////////////////////////////////////////////
void CMultiListBox::CalculateAvgCharWidth(CDC *pDC)
{
CFont *pCurrentFont=GetFont();
if(!pCurrentFont)
m_nAvgCharWidth=LOWORD(GetDialogBaseUnits());
else
{
CFont *pOldFont=pDC->SelectObject(pCurrentFont);
CSize size=pDC->GetTextExtent(m_strCharSet,m_strCharSet.GetLength());
m_nAvgCharWidth=MulDiv(1,size.cx,m_strCharSet.GetLength());
pDC->SelectObject(pOldFont);
}
}
////////////////////////////////////////////
//
////////////////////////////////////////////
void CMultiListBox::CalculateTabs()
{
UINT nIndex;
m_aTabs[0]=((m_aColWidth[0]+(m_nAvgCharWidth*m_nSpacing))*4)/m_nAvgCharWidth;
for(nIndex=1;nIndex<m_nTabs;nIndex++)
m_aTabs[nIndex]=m_aTabs[nIndex-1]+
((m_aColWidth[nIndex]+(m_nAvgCharWidth*m_nSpacing))*4)/m_nAvgCharWidth;
}
////////////////////////////////////////////
//
////////////////////////////////////////////
void CMultiListBox::Recalc()
{
m_aTabs.SetSize(MIN_TAB_SIZE);
m_aColWidth.SetSize(MIN_TAB_SIZE);
m_nTabs=MIN_TAB_SIZE;
InitColWidth();
CString str;
for(int nItem=GetCount()-1;nItem>=0;--nItem)
{
GetText(nItem,str);
CalculateColWidths(str);
}
CalculateTabs();
}
////////////////////////////////////////////
//
////////////////////////////////////////////
void CMultiListBox::InitColWidth()
{
UINT nIndex;
for(nIndex=0;nIndex<m_nTabs;nIndex++)
m_aColWidth[nIndex]=0;
}
////////////////////////////////////////////
//
////////////////////////////////////////////
BOOL CMultiListBox::CalculateColWidths(LPCSTR pString,BOOL bSetWidths)
{
BOOL bMaxColumn=FALSE;
CDC *pDC=GetDC();
UINT nCol=0;
if(pDC)
{
CalculateAvgCharWidth(pDC);
CFont *pOldFont=pDC->SelectObject(GetFont());
CString strRow;
CString strCol;
CSize size;
int nIndex=0;
strRow=pString;
while(nIndex!=-1)
{
if(nCol+1>m_nTabs)
{
m_aTabs.SetSize(m_nTabs+1);
m_aColWidth.SetSize(m_nTabs+1);
m_nTabs+=1;
}
if((nIndex=strRow.Find('\t'))==-1)
strCol=strRow;
else
{
strCol=strRow.Left(nIndex);
strRow=strRow.Mid(nIndex+1);
}
size=pDC->GetTextExtent(strCol,strCol.GetLength());
if((UINT)size.cx>=m_aColWidth[nCol])
{
bMaxColumn=TRUE;
if(bSetWidths)
m_aColWidth[nCol]=size.cx;
}
nCol++;
}
pDC->SelectObject(pOldFont);
ReleaseDC(pDC);
}
return bMaxColumn;
}
/////////////////////////////////////////////////////////////////
//
/////////////////////////////////////////////////////////////////
LRESULT CMultiListBox::OnAddString(WPARAM wParam,LPARAM lParam)
{
BOOL bRet=CalculateColWidths((LPCSTR)lParam);
if(bRet)
{
CalculateTabs();
SetTabStops(m_nTabs,(LPINT) &m_aTabs[0]);
int nOldScroll=GetHorizontalExtent();
int nNewScroll=0;
for(int i=0;i<(int)m_nTabs;i++)
{
nNewScroll+=m_aColWidth.GetAt(i);
if(i<(int)m_nTabs-1)
nNewScroll+=m_aTabs[i];
}
CRect rect;
GetClientRect(rect);
nNewScroll-=rect.Width();
if(nNewScroll>nOldScroll)
SetHorizontalExtent(nNewScroll);
}
return Default();
}
/////////////////////////////////////////////////////////////////
//
/////////////////////////////////////////////////////////////////
LRESULT CMultiListBox::OnInsertString(WPARAM wParam,LPARAM lParam)
{
BOOL bRet=CalculateColWidths((LPCSTR)lParam);
if(bRet)
{
CalculateTabs();
SetTabStops(m_nTabs,(LPINT) &m_aTabs[0]);
int nOldScroll=GetHorizontalExtent();
int nNewScroll=0;
for(int i=0;i<(int)m_nTabs;i++)
{
nNewScroll+=m_aColWidth.GetAt(i);
if(i<(int)m_nTabs-1)
nNewScroll+=m_aTabs[i];
}
CRect rect;
GetClientRect(rect);
nNewScroll-=rect.Width();
if(nNewScroll>nOldScroll)
SetHorizontalExtent(nNewScroll);
}
return Default();
}
/////////////////////////////////////////////////////////////////
//
/////////////////////////////////////////////////////////////////
LRESULT CMultiListBox::OnDeleteString(WPARAM wParam,LPARAM lParam)
{
CString str;
GetText(wParam,str);
BOOL bRecalc=CalculateColWidths(str,FALSE);
LRESULT lRet=Default();
if(bRecalc)
{
Recalc();
SetTabStops(m_nTabs,(LPINT) &m_aTabs[0]);
}
return lRet;
}
/////////////////////////////////////////////////////////////////
//
/////////////////////////////////////////////////////////////////
LRESULT CMultiListBox::OnResetContent(WPARAM wParam,LPARAM lParam)
{
m_aTabs.SetSize(MIN_TAB_SIZE);
m_aColWidth.SetSize(MIN_TAB_SIZE);
m_nTabs=MIN_TAB_SIZE;
InitColWidth();
SetHorizontalExtent(10);
return Default();
}
//////////////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////////////
CString CMultiListBox::GetColText(int nIndex,int nCol)
{
CString sText=_T("");
if(nIndex>=GetCount())
return sText;
GetText(nIndex,sText);
CString strRow=sText;
int nFind=0;
int j=0;
while(nFind!=-1)
{
if((nFind=strRow.Find('\t'))==-1)
{
if(nCol==j)
return strRow;
else
return _T("");
}
else
{
sText=strRow.Left(nFind);
strRow=strRow.Mid(nFind+1);
if(j==nCol)
return sText;
}
j++;
}
return sText;
}
//////////////////////////////////////////////////////////////////
//
//////////////////////////////////////////////////////////////////
void CMultiListBox::SetColText(int nIndex,int nCol,CString sNewText)
{
CString sText=_T("");
if(nIndex>=GetCount())
return;
GetText(nIndex,sText);
CString sOldText=sText;
CString strRow=sText;
CString sColText=_T("");
int nFind=0;
int j=0;
while(nFind!=-1)
{
if((nFind=strRow.Find('\t'))==-1)
{
if(nCol==j)
{
sColText=strRow;
break;
}
else
{
sColText=_T("");
break;
}
}
else
{
sColText=strRow.Left(nFind);
strRow=strRow.Mid(nFind+1);
if(j==nCol)
break;
}
j++;
}
sOldText.Replace(sColText,sNewText);
DeleteString(nIndex);
InsertString(nIndex,sOldText);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -