MadSerb
asked on
Very long MFC CListCtrl lists ?
I want to use CListCtrl list with many items (e.g. more then 30000), but it is impossible or very slow. Is there any solution for this problem? I will accept solutions with some other control, but with similar functionality.
You can turn the list control into a virtual list control. This is a new style implemented with the common controls version included with Internet Explorer 4.0 (among other places). It is also included with Visual C++ 6.0.
You simply have to handle two additional messages. On to provide feedback for a certain item requested by the control, and the other to manage a cache, in order to speed up things. YOu can find more information in http://msdn.microsoft.com, where they also have example code.
You simply have to handle two additional messages. On to provide feedback for a certain item requested by the control, and the other to manage a cache, in order to speed up things. YOu can find more information in http://msdn.microsoft.com, where they also have example code.
I can assure you the problem is not with the list control itself, simply your usage of it.
The most efficient use of a list control is via the Text Callback mechanism:
Using this mechanism in release code on a 500 MHz PII with 128M RAM and a fast Video Card I can fill the list with 100,000 rows in less than 7 seconds, this is about 15,000 rows per second. So for your 30,000 rows this would be about 2 seconds.
Note also, that I am using a relatively inefficient method for formatting the text on each row. The speed could be dramatically improved by doing something more sensible, I suspect that you could fill a list ctrl with 100,000 entries using something 'smarter' than sprintf in less than 1 second.
void CListDlg::OnGetdispinfoLis t1(NMHDR* pNMHDR, LRESULT* pResult)
{
LV_DISPINFO* pDispInfo = (LV_DISPINFO*)pNMHDR;
sprintf(pDispInfo->item.ps zText, "Text line %d", pDispInfo->item.iItem);
*pResult = 0;
}
void CListDlg::FillList()
{
CWaitCursor o;
m_List.SetRedraw(FALSE);
for(int i = 0; i < 100000; i++)
m_List.InsertItem(i, LPSTR_TEXTCALLBACK );
m_List.SetRedraw(TRUE);
}
void CListDlg::OnOK()
{
FillList();
}
The most efficient use of a list control is via the Text Callback mechanism:
Using this mechanism in release code on a 500 MHz PII with 128M RAM and a fast Video Card I can fill the list with 100,000 rows in less than 7 seconds, this is about 15,000 rows per second. So for your 30,000 rows this would be about 2 seconds.
Note also, that I am using a relatively inefficient method for formatting the text on each row. The speed could be dramatically improved by doing something more sensible, I suspect that you could fill a list ctrl with 100,000 entries using something 'smarter' than sprintf in less than 1 second.
void CListDlg::OnGetdispinfoLis
{
LV_DISPINFO* pDispInfo = (LV_DISPINFO*)pNMHDR;
sprintf(pDispInfo->item.ps
*pResult = 0;
}
void CListDlg::FillList()
{
CWaitCursor o;
m_List.SetRedraw(FALSE);
for(int i = 0; i < 100000; i++)
m_List.InsertItem(i, LPSTR_TEXTCALLBACK );
m_List.SetRedraw(TRUE);
}
void CListDlg::OnOK()
{
FillList();
}
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
U will find relevent info on microsoft web site
Regards