您的位置:首页 > 其它

OnCmdMsg 是 MFC 框架用来在窗口间分发消息用的

2013-03-15 10:53 381 查看
首先,OnCommand( )是在CWnd类中的,而OnCmdMsg( )是在CCmdTarget类中的。你如果看了MFC的类的继承图的话,你就会知道CWnd是从CCmdTarget类中继承的。下面是从MFC的源码中取出的片断,其中不难看到CWnd中的OnCommand( )调用了OnCmdMsg( );

/////////////////////////////////////////////////////////////////////////////

// CWnd command handling

BOOL CWnd::OnCommand(WPARAM wParam, LPARAM lParam)

// return TRUE if command invocation was attempted

{

UINT nID = LOWORD(wParam);

HWND hWndCtrl = (HWND)lParam;

int nCode = HIWORD(wParam);

// default routing for command messages (through closure table)

if (hWndCtrl == NULL)

{

// zero IDs for normal commands are not allowed

if (nID == 0)

return FALSE;

// make sure command has not become disabled before routing

CTestCmdUI state;

state.m_nID = nID;

OnCmdMsg(nID, CN_UPDATE_COMMAND_UI, &state, NULL);

if (!state.m_bEnabled)

{

TRACE1("Warning: not executing disabled command %d\n", nID);

return TRUE;

}

// menu or accelerator

nCode = CN_COMMAND;

}

else

{

// control notification

ASSERT(nID == 0 || ::IsWindow(hWndCtrl));

if (_afxThreadState->m_hLockoutNotifyWindow == m_hWnd)

return TRUE; // locked out - ignore control notification

// reflect notification to child window control

if (ReflectLastMsg(hWndCtrl))

return TRUE; // eaten by child

// zero IDs for normal commands are not allowed

if (nID == 0)

return FALSE;

}

#ifdef _DEBUG

if (nCode < 0 && nCode != (int)0x8000)

TRACE1("Implementation Warning: control notification = $%X.\n",

nCode);

#endif

return OnCmdMsg(nID, nCode, NULL, NULL);

}

其次,我的理解是,OnCommand( )主要是用来处理消息(控件,菜单,加速键)的;而OnCmdMsg( )主要是用来处理消息的路由的。路由就是各个类处理消息的顺序,在MFC中,标准的路由如下:(摘自MSDN)

Standard Command Route

When an object of this type receives a command . . . It gives itself and other command-target objects a chance to handle the command in this order:

MDI frame window

(CMDIFrameWnd)

1、Active CMDIChildWnd

2、This frame window

3、Application (CWinApp object)

Document frame window

(CFrameWnd, CMDIChildWnd)

1、Active view

2、This frame window

3、Application (CWinApp object)

View

1、This view

2、Document attached to the view

Document

1、This document

2、Document template attached to the document

Dialog box

1、This dialog box

2、Window that owns the dialog box

3、Application (CWinApp object)

下面这个例子也是摘自MSDN, 它重新定义了MFC的标准路由。

// This example illustrates extending the framework's standard command

// route from the view to objects managed by the view. This example

// is from an object-oriented drawing application, similar to the

// DRAWCLI sample application, which draws and edits "shapes".

BOOL CMyView::OnCmdMsg(UINT nID, int nCode, void* pExtra,

AFX_CMDHANDLERINFO* pHandlerInfo)

{

// Extend the framework's command route from the view to

// the application-specific CMyShape that is currently selected

// in the view. m_pActiveShape is NULL if no shape object

// is currently selected in the view.

if ((m_pActiveShape != NULL)

&& m_pActiveShape->OnCmdMsg(nID, nCode, pExtra, pHandlerInfo))

return TRUE;

// If the object(s) in the extended command route don't handle

// the command, then let the base class OnCmdMsg handle it.

return CView::OnCmdMsg(nID, nCode, pExtra, pHandlerInfo);

}

// The command handler for ID_SHAPE_COLOR (menu command to change

// the color of the currently selected shape) was added to

// the message map of CMyShape (note, not CMyView) using ClassWizard.

// The menu item will be automatically enabled or disabled, depending

// on whether a CMyShape is currently selected in the view, that is,

// depending on whether CMyView::m_pActiveView is NULL. It is not

// necessary to implement an ON_UPDATE_COMMAND_UI handler to enable

// or disable the menu item.

BEGIN_MESSAGE_MAP(CMyShape, CCmdTarget)

//{{AFX_MSG_MAP(CMyShape)

ON_COMMAND(ID_SHAPE_COLOR, OnShapeColor)

//}}AFX_MSG_MAP

END_MESSAGE_MAP()

http://bbs.csdn.net/topics/23919
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: