Определить горячую клавишу клавиатуры внутри элемента управления редактирования CComboBox
У меня есть этот код:
BOOL CChristianLifeMinistryStudentMaterialDlg::PreTranslateMessage(MSG* pMsg)
{
BOOL bNoDispatch, bDealtWith;
bDealtWith = FALSE;
if (IsCTRLpressed() &&
pMsg->message == WM_KEYDOWN && pMsg->wParam == _TINT(_T('I')))
{
if (EncodeText(pMsg->hwnd, _T("i")))
{
// Eat it.
bNoDispatch = TRUE;
bDealtWith = TRUE;
}
}
else if (IsCTRLpressed() &&
pMsg->message == WM_KEYDOWN && pMsg->wParam == _TINT(_T('B')))
{
if (EncodeText(pMsg->hwnd, _T("b")))
{
// Eat it.
bNoDispatch = TRUE;
bDealtWith = TRUE;
}
}
if (!bDealtWith)
bNoDispatch = CDialogEx::PreTranslateMessage(pMsg);
return bNoDispatch;
}
Изначально у меня было 3 CEdit
элементы управления в моем диалоге. Когда вы нажали эту клавишу, она выполнила действие, описанное выше, для выбора в элементах управления редактирования.
Я изменил управление с CEdit
в CComboBox
, Они редактируемого типа. Я настроил EncodeText
использовать GetEditSel
а также SetEditSel
,
Единственная проблема сейчас, когда я редактирую текст в поле со списком. Я выбираю часть текста и нажимаю CTRL + I, и ничего не происходит. PTM моего диалога не перехватывается.
Визуальный пример
В этом CEdit
контролировать я могу выбрать текст:
Затем я использую одну из горячих клавиш, например: CTRL + B, и она все еще работает:
Но когда я выбираю какой-то текст в редактируемый CComboBox
и используйте ту же горячую клавишу:
В этом случае это не работает.
Я предположил, что это потому, что технически я нахожусь внутри встроенного элемента управления "Редактировать" комбо. Как мне по-прежнему определять горячие клавиши сейчас, когда я использую выделенный текст внутри комбо?
2 ответа
Я закончил тем, что создал новый класс CEncodedCombBox
, происходит от CComboBox
, как это:
// EncodedComboBox.cpp : implementation file
//
#include "stdafx.h"
#include "Meeting Schedule Assistant.h"
#include "EncodedComboBox.h"
// CEncodedComboBox
IMPLEMENT_DYNAMIC(CEncodedComboBox, CComboBox)
CEncodedComboBox::CEncodedComboBox()
{
}
CEncodedComboBox::~CEncodedComboBox()
{
}
BEGIN_MESSAGE_MAP(CEncodedComboBox, CComboBox)
END_MESSAGE_MAP()
// CEncodedComboBox message handlers
BOOL CEncodedComboBox::PreTranslateMessage(MSG* pMsg)
{
BOOL bNoDispatch, bDealtWith;
DWORD dwSel = GetEditSel();
CString strCode = _T(""), strText;
GetWindowText(strText);
bDealtWith = FALSE;
if (IsCTRLpressed() &&
pMsg->message == WM_KEYDOWN && pMsg->wParam == _TINT(_T('I')))
{
strCode = _T("i");
bNoDispatch = TRUE;
bDealtWith = TRUE;
}
else if (IsCTRLpressed() &&
pMsg->message == WM_KEYDOWN && pMsg->wParam == _TINT(_T('B')))
{
strCode = _T("b");
bNoDispatch = TRUE;
bDealtWith = TRUE;
}
if (bDealtWith)
{
CMeetingScheduleAssistantApp::EncodeText(strText, strCode, LOWORD(dwSel), HIWORD(dwSel));
SetWindowText(strText);
SetEditSel(HIWORD(dwSel) + 7, HIWORD(dwSel) + 7);
}
if (!bDealtWith)
bNoDispatch = CComboBox::PreTranslateMessage(pMsg);
return bNoDispatch;
}
Как видите, он включает в себя PreTranslateMessage
и это работает:
Если есть лучший способ, тогда я приветствую ваши комментарии или ответ.
Обновить
Я должен был проверить на ручку управления редактирования, а не на ручку комбинированного окна для моего собственного CDialog
работать:
if (::GetParent(hWnd) == m_cbMaterialAssignment1.GetSafeHwnd())
Больше не требуется производный комбо-класс.
Не уверен, что мне нравится WM_KEYDOWN
хак. Если у вас есть настоящие горячие клавиши, я предлагаю вам правильно их обработать:
BEGIN_MESSAGE_MAP(CEncodedCombBox, CCombBox)
ON_WM_HOTKEY()
END_MESSAGE_MAP()
void CEncodedCombBox::OnHotKey(UINT nHotKeyId, UINT nKey1, UINT nKey2)
{
if (nHotKeyId == idForHotKey_I)
HandleCode(_T("i"));
else if (nHotKeyId == idForHotKey_B)
HandleCode(_T("b"));
}
void CEncodedCombBox::HandleCode(CString strCode)
{
DWORD dwSel = GetEditSel();
CMeetingScheduleAssistantApp::EncodeText(strText, strCode, LOWORD(dwSel), HIWORD(dwSel));
SetWindowText(strText);
SetEditSel(LOWORD(dwSel), HIWORD(dwSel) + 7);
}