int CALLBACK CMyView::SortCompareStringFunc(LPARAM lParam1, LPARAM lParam2, LPARAM lParamSort)
{
CMyView* pThis = (CMyView*)lParamSort;
int c ;
CString strItem1=_T(""), strItem2=_T(""); strItem1 = pThis->m_ctrlMainListClient.GetItemText(lParam1,pThis->m_nClickItem);
strItem2 = pThis->m_ctrlMainListClient.GetItemText(lParam2,pThis->m_nClickItem); c = strItem1.CompareNoCase(strItem2);
if(pThis->m_bCmpType)
   c = -c; return c;}
void CMyView::OnHdnItemclickListclient(NMHDR *pNMHDR, LRESULT *pResult)
{   
for(int i=0;i<m_ctrlMainListClient.GetItemCount();++i)
    m_ctrlMainListClient.SetItemData(i,i);//供排序使用的Item编号
    
LPNMHEADER phdr = reinterpret_cast<LPNMHEADER>(pNMHDR);
// TODO: 在此添加控件通知处理程序代码
if(phdr->iItem == m_nClickItem)
       m_bCmpType = ! m_bCmpType;
else
{
          m_bCmpType = TRUE;
  m_nClickItem = phdr->iItem; } m_ctrlMainListClient.SortItems(SortCompareStringFunc,(DWORD_PTR) this);
 
*pResult = 0;
}调试在回调函数里可以看到strItem1 ,strItem12读到了所点列的值,也进行了比较,返回了C,可最后执行完,列表里的内容就没了,找了好久资料也没解决,郁闷啊!

解决方案 »

  1.   

    提供一个笨办法哈,把数据放在CStringList里面,然后重新写到CListCtrl控件中
      

  2.   

    先谢谢zhaoyihui888 和cnzdgs ,这个主要是要实现点击列表头后下面的内容自动排序,就像系统的任务管理器那样.
    zhaoyihui888说的把数据放在CStringList里面,那样排序可能会很麻烦.
    代码方面其他好象和这个没联系了,最开始程序是能显示信息,但排不了序的
      

  3.   

    OnHdnItemclickListclient,从这个函数名来看,你响应的是HDN_ITEMCLICK通知,应该响应LVN_COLUMNCLICK通知才对。
      

  4.   

    cnzdgs 你说的LVN_COLUMNCLICK消息响应我试过,那样strItem1 ,strItem12都读不了列表里的内容.
    ......网上说的CListCtrl的排序都挺简单的,流程也清晰,可为什么我照做了就是不行呢?
      

  5.   

    没显示好象和
    for(int i=0;i <m_ctrlMainListClient.GetItemCount();++i) 
        m_ctrlMainListClient.SetItemData(i,i);//供排序使用的Item编号 
    有关系....我再看看
      

  6.   

    另外我程序采用的是Unicode编码,会不会是这里面的问题
      

  7.   

    实在是被这个问题折磨的受不了了,我最后决定放弃采用m_ctrlMainListClient.SortItems(SortCompareStringFunc,(DWORD_PTR) this)的方法,换成的下面的来解决.
    顺便简单总结下流程,也好让后来者少走弯路...
    m_ctrlMainListClient为我的CListCtrl控件名1.在含有ClistCtrl的父类中添加变量
                                      BOOL m_bCmpType;//是否顺序排序
                                      int  m_nClickItem ;//当前排序的列
    2.在资源中添加事件处理函数ON_NOTIFY(LVN_COLUMNCLICK, IDC_LIST1, OnLvnColumnclickListclient);
    3.void CMyView::OnLvnColumnclickListclient(NMHDR *pNMHDR, LRESULT *pResult)
    {
    //20081104
    // TODO: Add your control notification handler code here
    static int m_nClickItem = -1; // 保存当前的排序列。
    static BOOL m_bCmpType = TRUE;
    // 一开始表示为-1,表示尚未按任何列排序。    
    NM_LISTVIEW* phdr = (NM_LISTVIEW*)pNMHDR; if (m_nClickItem == phdr->iSubItem)
    {
    if (m_bCmpType)
    m_bCmpType = FALSE;
    else
    m_bCmpType = TRUE;
    }
    else
    {
    m_nClickItem = phdr->iSubItem;
    }
    m_nClickItem = phdr->iSubItem;
    SortTextItems(m_nClickItem, m_bCmpType, 0, -1);
    }BOOL CMyView::SortTextItems(int nCol, BOOL bAscending, int low, int high)
    {
    if( nCol >= m_ctrlMainListClient.GetHeaderCtrl()->GetItemCount() )//与列数比较
    return FALSE; if( high == -1 ) high = m_ctrlMainListClient.GetItemCount() - 1; int lo = low;
    int hi = high;
    CString midItem; if( hi <= lo ) return FALSE; midItem = m_ctrlMainListClient.GetItemText( (lo+hi)/2, nCol ); // loop through the list until indices cross
    while( lo <= hi )
    {
    // rowText will hold all column text for one row
    CStringArray rowText; // find the first element that is greater than or equal to 
    // the partition element starting from the left Index.
    if( bAscending )
    while( ( lo < high ) && ( m_ctrlMainListClient.GetItemText(lo, nCol) < midItem ) )
    ++lo;
    else
    while( ( lo < high ) && ( m_ctrlMainListClient.GetItemText(lo, nCol) > midItem ) )
    ++lo; // find an element that is smaller than or equal to 
    // the partition element starting from the right Index.
    if( bAscending )
    while( ( hi > low ) && ( m_ctrlMainListClient.GetItemText(hi, nCol) > midItem ) )
    --hi;
    else
    while( ( hi > low ) && ( m_ctrlMainListClient.GetItemText(hi, nCol) < midItem ) )
    --hi; // if the indexes have not crossed, swap
    // and if the items are not equal
    if( lo <= hi )
    {
    // swap only if the items are not equal
    if( m_ctrlMainListClient.GetItemText(lo, nCol) != m_ctrlMainListClient.GetItemText(hi, nCol))
    {
    // swap the rows
    LV_ITEM lvitemlo, lvitemhi;
    int nColCount = m_ctrlMainListClient.GetHeaderCtrl()->GetItemCount();//列数
    rowText.SetSize( nColCount );
    int i;
    for( i=0; i<nColCount; i++)
    rowText[i] = m_ctrlMainListClient.GetItemText(lo, i);
    lvitemlo.mask = LVIF_IMAGE | LVIF_PARAM | LVIF_STATE;
    lvitemlo.iItem = lo;
    lvitemlo.iSubItem = 0;
    lvitemlo.stateMask = LVIS_CUT | LVIS_DROPHILITED | 
    LVIS_FOCUSED |  LVIS_SELECTED | 
    LVIS_OVERLAYMASK | LVIS_STATEIMAGEMASK; lvitemhi = lvitemlo;
    lvitemhi.iItem = hi; m_ctrlMainListClient.GetItem( &lvitemlo );
    m_ctrlMainListClient.GetItem( &lvitemhi ); for( i=0; i<nColCount; i++)
    m_ctrlMainListClient.SetItemText(lo, i, m_ctrlMainListClient.GetItemText(hi, i)); lvitemhi.iItem = lo;
    m_ctrlMainListClient.SetItem( &lvitemhi ); for( i=0; i<nColCount; i++)
    m_ctrlMainListClient.SetItemText(hi, i, rowText[i]); lvitemlo.iItem = hi;
    m_ctrlMainListClient.SetItem( &lvitemlo );
    } ++lo;
    --hi;
    }
    } // If the right index has not reached the left side of array
    // must now sort the left partition.
    if( low < hi )
    SortTextItems( nCol, bAscending , low, hi);
    // If the left index has not reached the right side of array
    // must now sort the right partition.
    if( lo < high )
    SortTextItems( nCol, bAscending , lo, high );
    return TRUE;
    }
    先结帖了,再次感谢zhaoyihui888 和cnzdgs,如果大家谁有m_ctrlMainListClient.SortItems(SortCompareStringFunc,(DWORD_PTR) this)的解决方法,欢迎赐教,我会给分的
      

  8.   

    这样,你把代码发给我,我帮你调下吧,我觉得这个问题应该可以搞定,我QQ,175671267,邮箱[email protected]或者[email protected]