Уведомление об управлении деревом MFC запускается дважды

Моя проблема в том, что следующая функция вызывается дважды:

ON_NOTIFY(TVN_SELCHANGED, IDC_TREE1, &MainHamsterDlg::OnClickTree)

void MainHamsterDlg::OnClickTree(NMHDR* pNMHDR, LRESULT* pResult)
{
CTreeCtrl* pCtrl = (CTreeCtrl*)GetDlgItem(IDC_TREE1);
HTREEITEM hItem = pCtrl->GetSelectedItem();
BOOL hItemm = pCtrl->ItemHasChildren(hItem);
if (hItem && hItemm)
{
HTREEITEM hChild = pCtrl->GetChildItem(hItem);
pCtrl->SelectItem(hChild);                           <--- Cause of the "loop"}

*pResult = 1;
}

Мне нужен мой код для автоматического перехода к дочернему элементу дерева. (В будущем я напишу некоторый код, чтобы определить, что было выбрано, и это вызовет некоторые действия.)

Мой код работает правильно, когда я нажимаю на лист, потому что:

if (hItem && hItemm)

гарантирует, что:

pCtrl->SelectItem(hChild);

не будет выполнен Как я могу заставить мой код работать при нажатии на внутренний узел?

0

Решение

Я знаю, что это грязный хак, но он должен предотвратить выполнение вашего кода дважды. Добавьте следующий член в свой класс:

bool ignoreNextSelChange = false;

Затем измените вашу функцию следующим образом:

void MainHamsterDlg::OnClickTree(NMHDR* pNMHDR, LRESULT* pResult)
{
if (ignoreNextSelChange)
{
// Don't do anything, but make sure that the else block below will be executed
// again with the next (expected) call of this function.
ignoreNextSelChange = false;
}
else
{
CTreeCtrl* pCtrl = (CTreeCtrl*)GetDlgItem(IDC_TREE1);
HTREEITEM hItem = pCtrl->GetSelectedItem();
BOOL hItemm = pCtrl->ItemHasChildren(hItem);
if (hItem && hItemm)
{
HTREEITEM hChild = pCtrl->GetChildItem(hItem);

// Make sure that this else block won't be executed again when the function
// SelectItem() is called below.
ignoreNextSelChange = true;

pCtrl->SelectItem(hChild);
}
}
*pResult = 1;
}
2

Другие решения

В конце концов я нашел некоторый код, где решил подобную проблему. В этом коде я занимался TVN_SELCHANGING вместо TVN_SELCHANGED:

ON_NOTIFY(TVN_SELCHANGING, IDC_TREE1, &MainHamsterDlg::OnSelChanging)

void MainHamsterDlg::OnSelChanging(NMHDR* pNMHDR, LRESULT* pResult)
{
// Initially assume that the selection change is allowed.
*pResult = 0;

CTreeCtrl* pCtrl = (CTreeCtrl*)GetDlgItem(IDC_TREE1);
HTREEITEM hItem = pCtrl->GetSelectedItem();
BOOL hItemm = pCtrl->ItemHasChildren(hItem);
if (hItem && hItemm)
{
// Set *pResult to TRUE to prevent the selection from changing.
*pResult = TRUE;

// Make an own selection.
HTREEITEM hChild = pCtrl->GetChildItem(hItem);
pCtrl->SelectItem(hChild);
}
}

призвание SelectItem() в TVN_SELCHANGING Обработчик сообщений не доставляет мне проблем.

1

По вопросам рекламы [email protected]