1

我有一个简单的 MFC 应用程序:一个带有按钮的对话框。对于他们两个,我已经调用SetWindowContextHelpId()并将他们的上下文 ID 设置为非零值。

我还可以为帮助命令实现两个处理程序:OnCommandHelp(WPARAM wParam, LPARAM lParam)OnHelpInfo(HELPINFO* pHelpInfo).

MSDN 写了以下关于OnCommandHelp

lParam 包含当前可用的帮助上下文。如果没有确定帮助上下文,lParam 为零

但在我的情况下, lParam 始终为零,尽管pHelpInfo来自OnHelpInfo(HELPINFO* pHelpInfo)处理程序的处理程序包含有关控件的 ContextID 的正确非零信息(它是通过调用设置的SetWindowContextHelpId)。

现在我有两个问题:

1)为什么lParam总是零?MSDN 关于“确定帮助上下文”的评论是什么意思?什么是“当前可用的帮助上下文”?

OnCommandHelp2)如果我们可以使用,我们为什么需要OnHelpInfo

任何解释将不胜感激。

更新:

#include <afxwin.h>
#include <afxpriv.h>

#define ID_BUTTON 125

#define FRAME_HELP 4000
#define BUTTON_HELP 5000

class CMainWnd : public CFrameWnd
{
public:
    CMainWnd();
protected:
    afx_msg LRESULT OnCommandHelp(WPARAM wParam, LPARAM lParam);
    afx_msg int OnCreate(LPCREATESTRUCT lpcs);
    DECLARE_MESSAGE_MAP()
private:
    CButton btn;
};

BEGIN_MESSAGE_MAP(CMainWnd, CFrameWnd)
    ON_WM_CREATE()
    ON_MESSAGE(WM_COMMANDHELP, OnCommandHelp)
END_MESSAGE_MAP()

int CMainWnd::OnCreate(LPCREATESTRUCT lpcs)
{
    int res = CFrameWnd::OnCreate(lpcs);

    m_nIDHelp = FRAME_HELP;
    SetWindowContextHelpId(FRAME_HELP);

    CRect rc(0, 0, 100, 100);

    btn.Create(_T("Button"), WS_CHILD | WS_VISIBLE, rc, this, ID_BUTTON);

    btn.SetWindowContextHelpId(BUTTON_HELP);

    return res;
}

LRESULT CMainWnd::OnCommandHelp(WPARAM wParam, LPARAM lParam)
{
    wchar_t arr[20];
    _itow_s(lParam, arr, 10);
    MessageBox(arr);
    return TRUE;
}

CMainWnd::CMainWnd()
{
    Create(NULL, _T("Just a frame"));
}

class CApp : public CWinApp
{
public:
    virtual BOOL InitInstance() override;
    DECLARE_MESSAGE_MAP()
};

BEGIN_MESSAGE_MAP(CApp, CWinApp)
    ON_COMMAND(ID_HELP, OnHelp)
    ON_COMMAND(ID_HELP_FINDER, OnHelpFinder)
    ON_COMMAND(ID_HELP_INDEX, OnHelpIndex)
    ON_COMMAND(ID_HELP_USING, OnHelpUsing)
END_MESSAGE_MAP()

BOOL CApp::InitInstance()
{
    m_pMainWnd = new CMainWnd();
    m_pMainWnd->ShowWindow(m_nCmdShow);
    m_pMainWnd->UpdateWindow();

    return TRUE;
}

CApp App;
4

1 回答 1

1

理解函数嵌套的最简单方法是在 CDialog::OnCommandHelp 和 CWnd::OnHelpInfo 上设置断点。

首先将 WM_HELPINFO 发送到窗口。CWnd::OnHelpInfo 中的默认实现可能会处理它,并在稍后调用 OnCommandHelp。这里使用 m_nIDHelp 并启动​​帮助屏幕。

如果您自己处理 OnHelpInfo 处理程序中的所有内容,则不会调用 OnCommandHelp ...

事实上,这种复杂的结构是我们没有 SetWindowContextHelpId 时遗留下来的。

当我有一个正常的对话框并按 F1 时,我接到一个电话 OnCoammandHelp 并且 lParam 永远不会为 0!可能是因为我不处理 OnHelpInfo。如果您使用 OnHelpInfo,则上下文已经确定……原因是您这样做了,通过处理 OnHelpInfo。

于 2014-03-07T08:46:57.573 回答