三、程序代码
///////////////////////////////////////// #include "stdafx.h" // Generic dialog-that-uses-accelerators. class CDlgWithAccelerators : public CDialog { public: CDlgWithAccelerators(UINT nIDTemplate, CWnd* pParentWnd = NULL); CDlgWithAccelerators(LPCTSTR lpszTemplateName, CWnd* pParentWnd = NULL); ~CDlgWithAccelerators(); protected: HACCEL m_hAccel; // accelerator table // MFC overrides virtual BOOL OnInitDialog(); virtual BOOL PreTranslateMessage(MSG* pMsg); DECLARE_MESSAGE_MAP() };
/////////////////////////////////////////// // CDlgWithAccelerators is a general-purpose class that adds accelerators to CDialog. #include "stdafx.h" #include "dlgaccel.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif BEGIN_MESSAGE_MAP(CDlgWithAccelerators,CDialog) END_MESSAGE_MAP() CDlgWithAccelerators::CDlgWithAccelerators(LPCTSTR lpszTemplateName, CWnd* pParentWnd) : CDialog(lpszTemplateName, pParentWnd) {}
CDlgWithAccelerators::CDlgWithAccelerators(UINT nIDTemplate, CWnd* pParentWnd) : CDialog(nIDTemplate, pParentWnd) {}
CDlgWithAccelerators::~CDlgWithAccelerators() {}
/////////////////////////// Pre-translate message: translate keystrokes using acclerator table. BOOL CDlgWithAccelerators::PreTranslateMessage(MSG* pMsg) { if (WM_KEYFIRST <= pMsg->message && pMsg->message <= WM_KEYLAST) { HACCEL hAccel = m_hAccel; if (hAccel && ::TranslateAccelerator(m_hWnd, hAccel, pMsg)) return TRUE; } return CDialog::PreTranslateMessage(pMsg); }
//////////////////// Initialize dialog: load accelerators BOOL CDlgWithAccelerators::OnInitDialog() { BOOL bRet = CDialog::OnInitDialog(); // Load dialog's accelerators m_hAccel = ::LoadAccelerators(AfxGetResourceHandle(), m_lpszTemplateName); // use same resource name as dialog return bRet; }
///////////////////////////////////////////////////////////////////////// #include "stdafx.h" #include "resource.h" #include "dlgaccel.h" #include "TraceWin.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif
/////////////MFC app class CMyApp : public CWinApp { public: CMyApp(); ~CMyApp(); virtual BOOL InitInstance(); DECLARE_MESSAGE_MAP() };
CMyApp theApp; // THE one-and-only app
//////////// frame window class CMainFrame : public CFrameWnd { protected: virtual BOOL PreCreateWindow(CREATESTRUCT& cs); public: CMainFrame(); ~CMainFrame(); };
//////////////////// Typical dialog class CMyDlg : public CDlgWithAccelerators { public: CMyDlg(CWnd* pParent = NULL); // standard constructor protected: HICON m_hIcon; void NextInTabOrder(); // MFC overrides virtual BOOL OnInitDialog(); afx_msg void OnMyEnter(); afx_msg LRESULT OnGetDefID(WPARAM wp, LPARAM lp); DECLARE_MESSAGE_MAP() };
BEGIN_MESSAGE_MAP(CMyApp, CWinApp) END_MESSAGE_MAP()
CMyApp::CMyApp() { // nothing to do }
CMyApp::~CMyApp() { // nothing to do }
//////////////////// InitInstance: create dialog as child BOOL CMyApp::InitInstance() { // create frame window and load it CMainFrame* pFrame = new CMainFrame; m_pMainWnd = pFrame; pFrame->LoadFrame(IDR_MAINFRAME, WS_OVERLAPPED, NULL, NULL); CMyDlg dlg(pFrame); // create dialog and run it int nResponse = dlg.DoModal(); if (nResponse == IDOK) {} else if (nResponse == IDCANCEL) {} return FALSE; // quit }
CMainFrame::CMainFrame() { // nothing to do }
CMainFrame::~CMainFrame() { // nothing to do }
///////////// Pre-create window: set WS_EX_TOOLWINDOW style to hide dialog from task bar BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs) { if (CFrameWnd::PreCreateWindow(cs)) { cs.dwExStyle |= WS_EX_TOOLWINDOW; return TRUE; } return FALSE; }
BEGIN_MESSAGE_MAP(CMyDlg, CDlgWithAccelerators) ON_COMMAND(ID_MY_ENTER, OnMyEnter)
// The following is NOT needed since I am using accelerators to map // ENTER to ID_MY_ENTER. But if all you want to do is ignore the Enter key, // you can handle DM_GETDEFID as below. // ON_MESSAGE(DM_GETDEFID, OnGetDefID) // not used END_MESSAGE_MAP()
CMyDlg::CMyDlg(CWnd* pParent) : CDlgWithAccelerators(IDD_MYDIALOG, pParent) {}
//////////////////// Initialize dialog: BOOL CMyDlg::OnInitDialog() { CDlgWithAccelerators::OnInitDialog(); // Set the icon for this dialog. The framework does this automatically // when the application's main window is not a dialog m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME); ASSERT(m_hIcon); SetIcon(m_hIcon, TRUE); // Set big icon SetIcon(m_hIcon, FALSE); // Set small icon // use same resource name as dialog to load dialog's accelerators m_hAccel = ::LoadAccelerators(AfxGetResourceHandle(),m_lpszTemplateName); ASSERT(m_hAccel); return TRUE; // return TRUE unless you set the focus to a control }
//////////////////// This is called to handle ID_MY_ENTER--ie, Enter key. void CMyDlg::OnMyEnter() { TRACE(_T("CMyDlg::OnMyEnter/n")); NextInTabOrder(); // move to next control }
//////////////////// Helper function to move focus to the next control. void CMyDlg::NextInTabOrder() { CWnd* pWndNext = GetNextDlgTabItem(GetFocus()); if (pWndNext) { pWndNext->SetFocus(); } }
////////////////// // This function is not used, since its message map entry is commented out. // If all you want to do is ignore the Enter key (not map it to a command), // then all you have to do is return zero here. Note that you MUST return // the special code DC_HASDEFID in the high-order word!! LRESULT CMyDlg::OnGetDefID(WPARAM wp, LPARAM lp) { TRACE(_T("CMyDlg::OnGetDefID/n")); return MAKELONG(0,DC_HASDEFID); } |
四、小结
综上所述,MFC中为对话框添加加速键功能的方法就是:加载加速键和重载PreTranslateMessage()函数。也就是说,如果开发人员决定在对话框中使用加速键,不用去操心OnGetDefID()函数的处理,而是要重点实现加速键对应的WM_COMMAND消息响应处理函数。 
说明:本教程来源互联网或网友上传或出版商,仅为学习研究或媒体推广,wanshiok.com不保证资料的完整性。
2/2 首页 上一页 1 2 |