У меня есть диалог, полученный из CDialog, и я хочу закрыть его, как только пользователь уберет с него курсор мыши. Для этого я добавил обработчик OnMouseLeave, который вызывает OnCancel (). Насколько я понимаю, для своевременной отправки событий WM_MOUSELEAVE необходимо вызвать TrackMouseEvent внутри процедуры OnMouseMove. Итак, весь код выглядит следующим образом:
void CDlgMain::OnMouseLeave()
{
CDialog::OnMouseLeave();
// Close dialog when cursor is going out of it
OnCancel();
}
void CDlgMain::OnMouseMove(UINT nFlags, CPoint point)
{
TRACKMOUSEEVENT tme;
tme.cbSize = sizeof(tme);
tme.hwndTrack = m_hWnd;
tme.dwFlags = TME_LEAVE;
tme.dwHoverTime = HOVER_DEFAULT;
TrackMouseEvent(&tme);
CDialog::OnMouseMove(nFlags, point);
}
Работает нормально, но диалоговое окно закрывается, когда пользователь наводит на него некоторые дочерние элементы управления (например, кнопки, на которые он хочет нажать :)). Это происходит потому, что дочерние элементы управления не отправляют WM_MOUSEMOVE в родительский диалог.
Единственная функция, которую я нашел для "распространения" сообщений WM_MOUSEMOVE от дочерних элементов управления, - это SetCapture (). И это делает свою работу, но 1) пользователь не может нажать любую кнопку после этого и 2) значок мыши меняется на песочные часы. Так что это не вариант.
Есть предложения?
Обновление Я поместил вызов TrackMouseEvent в процедуру PreTranslateMessage, которая вызывается правильно при любых событиях перемещения мыши (даже при наведении на дочерние элементы управления). Странно то, что WM_MOUSELEAVE все еще генерируется, когда пользователь наводит на дочерний элемент управления! Похоже, TrackMouseEvent знает, какой элемент управления теперь находится. Есть идеи как это исправить?