我正在尝试获取MFC CListCtrl
中列的顺序。最初,我尝试在GetColumnOrderArray()
通知的消息处理程序中调用HDN_ENDDRAG
,但始终返回旧的(预拖放)列顺序。因此,根据this SO帖子评论中的建议,我尝试同时处理HDN_BEGINDRAG
和HDN_ENDDRAG
,并使用phdr->pitem->iOrder
获取旧列和新列。但是pitem
对我来说在两个处理程序中总是为NULL。不知道为什么。
SOOO我尝试使用存储在消息(phdr->iItem
)中的列索引直接与CHeaderCtrl
对话并自己获取列顺序,但是我的标题控件填充的结构中的字段是都无效;我仍然无法获得列顺序。
我的列表控件是否存在某种更深层次的问题?或者我只是错误地处理消息?
HDN_BEGINDRAG
消息处理程序:
BOOL CDFAManListView::OnHdnBegindrag(UINT, NMHDR *pNMHDR, LRESULT *pResult)
{
LPNMHEADER phdr = reinterpret_cast<LPNMHEADER>(pNMHDR);
phdr->iItem; // this contains a valid column index
HDITEM columnStruct;
List->GetHeaderCtrl()->GetItem(phdr->iItem, &columnStruct); // but this call just fills columnStruct with junk values
if (phdr->pitem) // pitem is always null
{
initialPosition = phdr->pitem->iOrder;
}
*pResult = 0;
return TRUE;
}
HDN_ENDDRAG
消息处理程序:
void CDFAManListView::OnHdnEnddrag(NMHDR *pNMHDR, LRESULT *pResult)
{
LPNMHEADER phdr = reinterpret_cast<LPNMHEADER>(pNMHDR);
HDITEM columnStruct;
List->GetHeaderCtrl()->GetItem(phdr->iItem, &columnStruct); // still just fills columnStruct with junk
List->GetColumnOrderArray(signalColumnOrder); // gets **old** column order
*pResult = 0;
}
答案 0 :(得分:0)
这可能是一个简单的解决方案,为什么不在列表控件的父级需要关闭时调用GetColumnOrderArray()
?
如果您确实需要立即将列顺序用于其他目的,并且从您引用的SO帖子中看到,HDN_ENDDRAG
似乎为时过早,请致电GetColumnOrderArray()
,尝试PostMessage
到OnHdnEnddrag()
末尾的列表控件的(父级),消息号在WM_USER through 0x7FFF
范围内,并在该消息的处理程序中调用GetColumnOrderArray()
。
答案 1 :(得分:0)
虽然这是一个老问题,但我刚看到CListCtrl列拖动时遇到它并认为我会更新它以防其他人使用它。
OP提到了,
HDITEM columnStruct;
List->GetHeaderCtrl()->GetItem(phdr->iItem, &columnStruct); // but this call just fills columnStruct with junk values
这是因为你没有初始化columnStruct,足以告诉GetItem你有兴趣检索哪些数据。您需要使用各种标志(如HDI_WIDTH |)初始化columnStruct.mask HDI_ORDER,如果你使用HDI_TEXT,那么给columnStruct.pszText一个缓冲区和columnStruct.cchTextMax缓冲区的大小。
例如documented in the CHeaderCtrl::GetItem documentation on MSDN。
mask元素中设置的任何标志都确保了值中的值 返回时适当填写相应的元素。如果是面具 element设置为零,其他结构元素中的值为 无意义的。