mfc listctr 选中一行后 再点击界面外 选中的那行如何保持选中
时间: 2024-10-15 18:13:22 浏览: 25
在MFC(Microsoft Foundation Classes)中,特别是使用CListCtrl控件时,如果希望用户选择某一行后即使离开控制区域该行仍然保持选中状态,你可以通过处理`NM_DBLCLK`(双击事件)和`LBN_ITEMCHANGED`(列表项更改事件)来实现。
1. 首先,在`OnDblclk`函数中,当用户双击某一行时,可以设置选中状态并记住当前选中的索引:
```cpp
void CYourClass::OnDblclk(NMHDR *pNMHDR, LRESULT* pResult)
{
LPNMITEMACTIVATE lpItemActivate = reinterpret_cast<LPNMITEMACTIVATE>(pNMHDR);
if (lpItemActivate && lpItemActivate->itemFrom == GetCurSel())
{
// 设置选中
SetSel(lpItemActivate->itemFrom, TRUE);
// 记录下选中的索引或对象
m_selectedIndex = lpItemActivate->itemFrom;
}
*pResult = 0;
}
```
2. 然后,在`OnItemStateChanged`函数中(或在其他合适的地方),检查是否在界面之外改变了选中状态,并恢复之前的选中:
```cpp
void CYourClass::OnItemStateChanged(CCmdUI* pCmdUI, NMHDR* pNMHDR, LRESULT* pResult)
{
if (HIWORD(pNMHDR->code) == LVN_KEYDOWN || HIWORD(pNMHDR->code) == LVN_BEGINLABELEDIT)
{
int newSel = GetNextItem(-1, LVNI_FOCUSED);
if (newSel != m_selectedIndex)
{
// 如果新的选中不是之前保存的那个,恢复选中
SetSel(m_selectedIndex, TRUE);
}
}
*pResult = 0;
}
// 在窗口初始化时注册这两个消息处理器
BOOL CYourClass::PreCreateWindow(CREATESTRUCT& cs)
{
// ... 其他创建窗口的代码 ...
// 注册双击事件
cs.style &= ~WS_VSCROLL; // 取消垂直滚动条,以便处理双击事件
cs.style |= WS_TABSTOP;
return CDialog::PreCreateWindow(cs);
}
// 在窗口显示前,添加列表项改变监听器
void CYourClass::OnInitDialog()
{
// ... 初始化列表控件的其他属性 ...
// 添加列表项改变监听器
CListCtrl::Set_NOTIFY(LVN_ITEMCHANGED, OnItemStateChanged);
}
```
这样,当你离开列表框范围时,只要用户有焦点变化(如按键或失去焦点),就会检测到并尝试恢复之前的选择。
阅读全文